Merge pull request #2254 from vector-im/feature/bma/cleanup

Feature/bma/cleanup
This commit is contained in:
Benoit Marty 2020-10-13 16:49:51 +02:00 committed by GitHub
commit cf98252bdb
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
287 changed files with 730 additions and 1081 deletions

View file

@ -4,16 +4,7 @@
<JetCodeStyleSettings> <JetCodeStyleSettings>
<option name="PACKAGES_TO_USE_STAR_IMPORTS"> <option name="PACKAGES_TO_USE_STAR_IMPORTS">
<value> <value>
<package name="kotlinx.android.synthetic" alias="false" withSubpackages="true" /> <package name="kotlinx.android.synthetic" withSubpackages="true" static="false" />
</value>
</option>
<option name="PACKAGES_IMPORT_LAYOUT">
<value>
<package name="" alias="false" withSubpackages="true" />
<package name="java" alias="false" withSubpackages="true" />
<package name="javax" alias="false" withSubpackages="true" />
<package name="kotlin" alias="false" withSubpackages="true" />
<package name="" alias="true" withSubpackages="true" />
</value> </value>
</option> </option>
<option name="ALIGN_IN_COLUMNS_CASE_BRANCH" value="true" /> <option name="ALIGN_IN_COLUMNS_CASE_BRANCH" value="true" />

View file

@ -42,4 +42,4 @@ interface MatrixCallback<in T> {
/** /**
* Basic no op implementation * Basic no op implementation
*/ */
class NoOpMatrixCallback<T>: MatrixCallback<T> class NoOpMatrixCallback<T> : MatrixCallback<T>

View file

@ -48,18 +48,25 @@ data class MatrixError(
companion object { companion object {
/** Forbidden access, e.g. joining a room without permission, failed login. */ /** Forbidden access, e.g. joining a room without permission, failed login. */
const val M_FORBIDDEN = "M_FORBIDDEN" const val M_FORBIDDEN = "M_FORBIDDEN"
/** An unknown error has occurred. */ /** An unknown error has occurred. */
const val M_UNKNOWN = "M_UNKNOWN" const val M_UNKNOWN = "M_UNKNOWN"
/** The access token specified was not recognised. */ /** The access token specified was not recognised. */
const val M_UNKNOWN_TOKEN = "M_UNKNOWN_TOKEN" const val M_UNKNOWN_TOKEN = "M_UNKNOWN_TOKEN"
/** No access token was specified for the request. */ /** No access token was specified for the request. */
const val M_MISSING_TOKEN = "M_MISSING_TOKEN" const val M_MISSING_TOKEN = "M_MISSING_TOKEN"
/** Request contained valid JSON, but it was malformed in some way, e.g. missing required keys, invalid values for keys. */ /** Request contained valid JSON, but it was malformed in some way, e.g. missing required keys, invalid values for keys. */
const val M_BAD_JSON = "M_BAD_JSON" const val M_BAD_JSON = "M_BAD_JSON"
/** Request did not contain valid JSON. */ /** Request did not contain valid JSON. */
const val M_NOT_JSON = "M_NOT_JSON" const val M_NOT_JSON = "M_NOT_JSON"
/** No resource was found for this request. */ /** No resource was found for this request. */
const val M_NOT_FOUND = "M_NOT_FOUND" const val M_NOT_FOUND = "M_NOT_FOUND"
/** Too many requests have been sent in a short period of time. Wait a while then try again. */ /** Too many requests have been sent in a short period of time. Wait a while then try again. */
const val M_LIMIT_EXCEEDED = "M_LIMIT_EXCEEDED" const val M_LIMIT_EXCEEDED = "M_LIMIT_EXCEEDED"
@ -69,68 +76,97 @@ data class MatrixError(
/** Encountered when trying to register a user ID which has been taken. */ /** Encountered when trying to register a user ID which has been taken. */
const val M_USER_IN_USE = "M_USER_IN_USE" const val M_USER_IN_USE = "M_USER_IN_USE"
/** Sent when the room alias given to the createRoom API is already in use. */ /** Sent when the room alias given to the createRoom API is already in use. */
const val M_ROOM_IN_USE = "M_ROOM_IN_USE" const val M_ROOM_IN_USE = "M_ROOM_IN_USE"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_BAD_PAGINATION = "M_BAD_PAGINATION" const val M_BAD_PAGINATION = "M_BAD_PAGINATION"
/** The request was not correctly authorized. Usually due to login failures. */ /** The request was not correctly authorized. Usually due to login failures. */
const val M_UNAUTHORIZED = "M_UNAUTHORIZED" const val M_UNAUTHORIZED = "M_UNAUTHORIZED"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_OLD_VERSION = "M_OLD_VERSION" const val M_OLD_VERSION = "M_OLD_VERSION"
/** The server did not understand the request. */ /** The server did not understand the request. */
const val M_UNRECOGNIZED = "M_UNRECOGNIZED" const val M_UNRECOGNIZED = "M_UNRECOGNIZED"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_LOGIN_EMAIL_URL_NOT_YET = "M_LOGIN_EMAIL_URL_NOT_YET" const val M_LOGIN_EMAIL_URL_NOT_YET = "M_LOGIN_EMAIL_URL_NOT_YET"
/** Authentication could not be performed on the third party identifier. */ /** Authentication could not be performed on the third party identifier. */
const val M_THREEPID_AUTH_FAILED = "M_THREEPID_AUTH_FAILED" const val M_THREEPID_AUTH_FAILED = "M_THREEPID_AUTH_FAILED"
/** Sent when a threepid given to an API cannot be used because no record matching the threepid was found. */ /** Sent when a threepid given to an API cannot be used because no record matching the threepid was found. */
const val M_THREEPID_NOT_FOUND = "M_THREEPID_NOT_FOUND" const val M_THREEPID_NOT_FOUND = "M_THREEPID_NOT_FOUND"
/** Sent when a threepid given to an API cannot be used because the same threepid is already in use. */ /** Sent when a threepid given to an API cannot be used because the same threepid is already in use. */
const val M_THREEPID_IN_USE = "M_THREEPID_IN_USE" const val M_THREEPID_IN_USE = "M_THREEPID_IN_USE"
/** The client's request used a third party server, eg. identity server, that this server does not trust. */ /** The client's request used a third party server, eg. identity server, that this server does not trust. */
const val M_SERVER_NOT_TRUSTED = "M_SERVER_NOT_TRUSTED" const val M_SERVER_NOT_TRUSTED = "M_SERVER_NOT_TRUSTED"
/** The request or entity was too large. */ /** The request or entity was too large. */
const val M_TOO_LARGE = "M_TOO_LARGE" const val M_TOO_LARGE = "M_TOO_LARGE"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_CONSENT_NOT_GIVEN = "M_CONSENT_NOT_GIVEN" const val M_CONSENT_NOT_GIVEN = "M_CONSENT_NOT_GIVEN"
/** The request cannot be completed because the homeserver has reached a resource limit imposed on it. For example, /** The request cannot be completed because the homeserver has reached a resource limit imposed on it. For example,
* a homeserver held in a shared hosting environment may reach a resource limit if it starts using too much memory * a homeserver held in a shared hosting environment may reach a resource limit if it starts using too much memory
* or disk space. The error MUST have an admin_contact field to provide the user receiving the error a place to reach * or disk space. The error MUST have an admin_contact field to provide the user receiving the error a place to reach
* out to. Typically, this error will appear on routes which attempt to modify state (eg: sending messages, account * out to. Typically, this error will appear on routes which attempt to modify state (eg: sending messages, account
* data, etc) and not routes which only read state (eg: /sync, get account data, etc). */ * data, etc) and not routes which only read state (eg: /sync, get account data, etc). */
const val M_RESOURCE_LIMIT_EXCEEDED = "M_RESOURCE_LIMIT_EXCEEDED" const val M_RESOURCE_LIMIT_EXCEEDED = "M_RESOURCE_LIMIT_EXCEEDED"
/** The user ID associated with the request has been deactivated. Typically for endpoints that prove authentication, such as /login. */ /** The user ID associated with the request has been deactivated. Typically for endpoints that prove authentication, such as /login. */
const val M_USER_DEACTIVATED = "M_USER_DEACTIVATED" const val M_USER_DEACTIVATED = "M_USER_DEACTIVATED"
/** Encountered when trying to register a user ID which is not valid. */ /** Encountered when trying to register a user ID which is not valid. */
const val M_INVALID_USERNAME = "M_INVALID_USERNAME" const val M_INVALID_USERNAME = "M_INVALID_USERNAME"
/** Sent when the initial state given to the createRoom API is invalid. */ /** Sent when the initial state given to the createRoom API is invalid. */
const val M_INVALID_ROOM_STATE = "M_INVALID_ROOM_STATE" const val M_INVALID_ROOM_STATE = "M_INVALID_ROOM_STATE"
/** The server does not permit this third party identifier. This may happen if the server only permits, /** The server does not permit this third party identifier. This may happen if the server only permits,
* for example, email addresses from a particular domain. */ * for example, email addresses from a particular domain. */
const val M_THREEPID_DENIED = "M_THREEPID_DENIED" const val M_THREEPID_DENIED = "M_THREEPID_DENIED"
/** The client's request to create a room used a room version that the server does not support. */ /** The client's request to create a room used a room version that the server does not support. */
const val M_UNSUPPORTED_ROOM_VERSION = "M_UNSUPPORTED_ROOM_VERSION" const val M_UNSUPPORTED_ROOM_VERSION = "M_UNSUPPORTED_ROOM_VERSION"
/** The client attempted to join a room that has a version the server does not support. /** The client attempted to join a room that has a version the server does not support.
* Inspect the room_version property of the error response for the room's version. */ * Inspect the room_version property of the error response for the room's version. */
const val M_INCOMPATIBLE_ROOM_VERSION = "M_INCOMPATIBLE_ROOM_VERSION" const val M_INCOMPATIBLE_ROOM_VERSION = "M_INCOMPATIBLE_ROOM_VERSION"
/** The state change requested cannot be performed, such as attempting to unban a user who is not banned. */ /** The state change requested cannot be performed, such as attempting to unban a user who is not banned. */
const val M_BAD_STATE = "M_BAD_STATE" const val M_BAD_STATE = "M_BAD_STATE"
/** The room or resource does not permit guests to access it. */ /** The room or resource does not permit guests to access it. */
const val M_GUEST_ACCESS_FORBIDDEN = "M_GUEST_ACCESS_FORBIDDEN" const val M_GUEST_ACCESS_FORBIDDEN = "M_GUEST_ACCESS_FORBIDDEN"
/** A Captcha is required to complete the request. */ /** A Captcha is required to complete the request. */
const val M_CAPTCHA_NEEDED = "M_CAPTCHA_NEEDED" const val M_CAPTCHA_NEEDED = "M_CAPTCHA_NEEDED"
/** The Captcha provided did not match what was expected. */ /** The Captcha provided did not match what was expected. */
const val M_CAPTCHA_INVALID = "M_CAPTCHA_INVALID" const val M_CAPTCHA_INVALID = "M_CAPTCHA_INVALID"
/** A required parameter was missing from the request. */ /** A required parameter was missing from the request. */
const val M_MISSING_PARAM = "M_MISSING_PARAM" const val M_MISSING_PARAM = "M_MISSING_PARAM"
/** A parameter that was specified has the wrong value. For example, the server expected an integer and instead received a string. */ /** A parameter that was specified has the wrong value. For example, the server expected an integer and instead received a string. */
const val M_INVALID_PARAM = "M_INVALID_PARAM" const val M_INVALID_PARAM = "M_INVALID_PARAM"
/** The resource being requested is reserved by an application service, or the application service making the request has not created the resource. */ /** The resource being requested is reserved by an application service, or the application service making the request has not created the resource. */
const val M_EXCLUSIVE = "M_EXCLUSIVE" const val M_EXCLUSIVE = "M_EXCLUSIVE"
/** The user is unable to reject an invite to join the server notices room. See the Server Notices module for more information. */ /** The user is unable to reject an invite to join the server notices room. See the Server Notices module for more information. */
const val M_CANNOT_LEAVE_SERVER_NOTICE_ROOM = "M_CANNOT_LEAVE_SERVER_NOTICE_ROOM" const val M_CANNOT_LEAVE_SERVER_NOTICE_ROOM = "M_CANNOT_LEAVE_SERVER_NOTICE_ROOM"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_WRONG_ROOM_KEYS_VERSION = "M_WRONG_ROOM_KEYS_VERSION" const val M_WRONG_ROOM_KEYS_VERSION = "M_WRONG_ROOM_KEYS_VERSION"
/** (Not documented yet) */ /** (Not documented yet) */
const val M_WEAK_PASSWORD = "M_WEAK_PASSWORD" const val M_WEAK_PASSWORD = "M_WEAK_PASSWORD"

View file

@ -71,15 +71,15 @@ sealed class Action {
fun List<Action>.toJson(): List<Any> { fun List<Action>.toJson(): List<Any> {
return map { action -> return map { action ->
when (action) { when (action) {
is Action.Notify -> Action.ACTION_NOTIFY is Action.Notify -> Action.ACTION_NOTIFY
is Action.DoNotNotify -> Action.ACTION_DONT_NOTIFY is Action.DoNotNotify -> Action.ACTION_DONT_NOTIFY
is Action.Sound -> { is Action.Sound -> {
mapOf( mapOf(
Action.ACTION_OBJECT_SET_TWEAK_KEY to Action.ACTION_OBJECT_SET_TWEAK_VALUE_SOUND, Action.ACTION_OBJECT_SET_TWEAK_KEY to Action.ACTION_OBJECT_SET_TWEAK_VALUE_SOUND,
Action.ACTION_OBJECT_VALUE_KEY to action.sound Action.ACTION_OBJECT_VALUE_KEY to action.sound
) )
} }
is Action.Highlight -> { is Action.Highlight -> {
mapOf( mapOf(
Action.ACTION_OBJECT_SET_TWEAK_KEY to Action.ACTION_OBJECT_SET_TWEAK_VALUE_HIGHLIGHT, Action.ACTION_OBJECT_SET_TWEAK_KEY to Action.ACTION_OBJECT_SET_TWEAK_VALUE_HIGHLIGHT,
Action.ACTION_OBJECT_VALUE_KEY to action.highlight Action.ACTION_OBJECT_VALUE_KEY to action.highlight
@ -94,9 +94,9 @@ fun PushRule.getActions(): List<Action> {
actions.forEach { actionStrOrObj -> actions.forEach { actionStrOrObj ->
when (actionStrOrObj) { when (actionStrOrObj) {
Action.ACTION_NOTIFY -> Action.Notify Action.ACTION_NOTIFY -> Action.Notify
Action.ACTION_DONT_NOTIFY -> Action.DoNotNotify Action.ACTION_DONT_NOTIFY -> Action.DoNotNotify
is Map<*, *> -> { is Map<*, *> -> {
when (actionStrOrObj[Action.ACTION_OBJECT_SET_TWEAK_KEY]) { when (actionStrOrObj[Action.ACTION_OBJECT_SET_TWEAK_KEY]) {
Action.ACTION_OBJECT_SET_TWEAK_VALUE_SOUND -> { Action.ACTION_OBJECT_SET_TWEAK_VALUE_SOUND -> {
(actionStrOrObj[Action.ACTION_OBJECT_VALUE_KEY] as? String)?.let { stringValue -> (actionStrOrObj[Action.ACTION_OBJECT_VALUE_KEY] as? String)?.let { stringValue ->
@ -112,13 +112,13 @@ fun PushRule.getActions(): List<Action> {
// When the value is not there, default is true, says the spec // When the value is not there, default is true, says the spec
?: Action.Highlight(true) ?: Action.Highlight(true)
} }
else -> { else -> {
Timber.w("Unsupported set_tweak value ${actionStrOrObj[Action.ACTION_OBJECT_SET_TWEAK_KEY]}") Timber.w("Unsupported set_tweak value ${actionStrOrObj[Action.ACTION_OBJECT_SET_TWEAK_KEY]}")
null null
} }
} }
} }
else -> { else -> {
Timber.w("Unsupported action type $actionStrOrObj") Timber.w("Unsupported action type $actionStrOrObj")
null null
} }

View file

@ -18,12 +18,12 @@ package org.matrix.android.sdk.api.raw
sealed class RawCacheStrategy { sealed class RawCacheStrategy {
// Data is always fetched from the server // Data is always fetched from the server
object NoCache: RawCacheStrategy() object NoCache : RawCacheStrategy()
// Once data is retrieved, it is stored for the provided amount of time. // Once data is retrieved, it is stored for the provided amount of time.
// In case of error, and if strict is set to false, the cache can be returned if available // In case of error, and if strict is set to false, the cache can be returned if available
data class TtlCache(val validityDurationInMillis: Long, val strict: Boolean): RawCacheStrategy() data class TtlCache(val validityDurationInMillis: Long, val strict: Boolean) : RawCacheStrategy()
// Once retrieved, the data is stored in cache and will be always get from the cache // Once retrieved, the data is stored in cache and will be always get from the cache
object InfiniteCache: RawCacheStrategy() object InfiniteCache : RawCacheStrategy()
} }

View file

@ -32,7 +32,7 @@ interface CallSignalingService {
fun removeCallListener(listener: CallsListener) fun removeCallListener(listener: CallsListener)
fun getCallWithId(callId: String) : MxCall? fun getCallWithId(callId: String): MxCall?
fun isThereAnyActiveCall(): Boolean fun isThereAnyActiveCall(): Boolean
} }

View file

@ -33,6 +33,7 @@ interface MxCallDetail {
interface MxCall : MxCallDetail { interface MxCall : MxCallDetail {
var state: CallState var state: CallState
/** /**
* Pick Up the incoming call * Pick Up the incoming call
* It has no effect on outgoing call * It has no effect on outgoing call

View file

@ -101,9 +101,9 @@ interface CryptoService {
fun fetchDevicesList(callback: MatrixCallback<DevicesListResponse>) fun fetchDevicesList(callback: MatrixCallback<DevicesListResponse>)
fun getMyDevicesInfo() : List<DeviceInfo> fun getMyDevicesInfo(): List<DeviceInfo>
fun getLiveMyDevicesInfo() : LiveData<List<DeviceInfo>> fun getLiveMyDevicesInfo(): LiveData<List<DeviceInfo>>
fun getDeviceInfo(deviceId: String, callback: MatrixCallback<DeviceInfo>) fun getDeviceInfo(deviceId: String, callback: MatrixCallback<DeviceInfo>)
@ -148,6 +148,6 @@ interface CryptoService {
fun getGossipingEventsTrail(): List<Event> fun getGossipingEventsTrail(): List<Event>
// For testing shared session // For testing shared session
fun getSharedWithInfo(roomId: String?, sessionId: String) : MXUsersDevicesMap<Int> fun getSharedWithInfo(roomId: String?, sessionId: String): MXUsersDevicesMap<Int>
fun getWithHeldMegolmSession(roomId: String, sessionId: String) : RoomKeyWithHeldContent? fun getWithHeldMegolmSession(roomId: String, sessionId: String): RoomKeyWithHeldContent?
} }

View file

@ -216,7 +216,7 @@ interface KeysBackupService {
// For gossiping // For gossiping
fun saveBackupRecoveryKey(recoveryKey: String?, version: String?) fun saveBackupRecoveryKey(recoveryKey: String?, version: String?)
fun getKeyBackupRecoveryKeyInfo() : SavedKeyBackupKeyInfo? fun getKeyBackupRecoveryKeyInfo(): SavedKeyBackupKeyInfo?
fun isValidRecoveryKeyForCurrentVersion(recoveryKey: String, callback: MatrixCallback<Boolean>) fun isValidRecoveryKeyForCurrentVersion(recoveryKey: String, callback: MatrixCallback<Boolean>)
} }

View file

@ -53,23 +53,31 @@ package org.matrix.android.sdk.api.session.crypto.keysbackup
enum class KeysBackupState { enum class KeysBackupState {
// Need to check the current backup version on the homeserver // Need to check the current backup version on the homeserver
Unknown, Unknown,
// Checking if backup is enabled on home server // Checking if backup is enabled on home server
CheckingBackUpOnHomeserver, CheckingBackUpOnHomeserver,
// Backup has been stopped because a new backup version has been detected on the homeserver // Backup has been stopped because a new backup version has been detected on the homeserver
WrongBackUpVersion, WrongBackUpVersion,
// Backup from this device is not enabled // Backup from this device is not enabled
Disabled, Disabled,
// There is a backup available on the homeserver but it is not trusted. // There is a backup available on the homeserver but it is not trusted.
// It is not trusted because the signature is invalid or the device that created it is not verified // It is not trusted because the signature is invalid or the device that created it is not verified
// Use [KeysBackup.getKeysBackupTrust()] to get trust details. // Use [KeysBackup.getKeysBackupTrust()] to get trust details.
// Consequently, the backup from this device is not enabled. // Consequently, the backup from this device is not enabled.
NotTrusted, NotTrusted,
// Backup is being enabled: the backup version is being created on the homeserver // Backup is being enabled: the backup version is being created on the homeserver
Enabling, Enabling,
// Backup is enabled and ready to send backup to the homeserver // Backup is enabled and ready to send backup to the homeserver
ReadyToBackUp, ReadyToBackUp,
// e2e keys are going to be sent to the homeserver // e2e keys are going to be sent to the homeserver
WillBackUp, WillBackUp,
// e2e keys are being sent to the homeserver // e2e keys are being sent to the homeserver
BackingUp BackingUp
} }

View file

@ -35,7 +35,7 @@ interface GossipingRequestListener {
* Returns the secret value to be shared * Returns the secret value to be shared
* @return true if is handled * @return true if is handled
*/ */
fun onSecretShareRequest(request: IncomingSecretShareRequest) : Boolean fun onSecretShareRequest(request: IncomingSecretShareRequest): Boolean
/** /**
* A room key request cancellation has been received. * A room key request cancellation has been received.

View file

@ -22,8 +22,10 @@ package org.matrix.android.sdk.api.session.crypto.verification
enum class VerificationMethod { enum class VerificationMethod {
// Use it when your application supports the SAS verification method // Use it when your application supports the SAS verification method
SAS, SAS,
// Use it if your application is able to display QR codes // Use it if your application is able to display QR codes
QR_CODE_SHOW, QR_CODE_SHOW,
// Use it if your application is able to scan QR codes // Use it if your application is able to scan QR codes
QR_CODE_SCAN QR_CODE_SCAN
} }

View file

@ -253,6 +253,7 @@ fun Event.isFileMessage(): Boolean {
else -> false else -> false
} }
} }
fun Event.isAttachmentMessage(): Boolean { fun Event.isAttachmentMessage(): Boolean {
return getClearType() == EventType.MESSAGE return getClearType() == EventType.MESSAGE
&& when (getClearContent()?.toModel<MessageContent>()?.msgType) { && when (getClearContent()?.toModel<MessageContent>()?.msgType) {

View file

@ -21,10 +21,13 @@ package org.matrix.android.sdk.api.session.events.model
object RelationType { object RelationType {
/** Lets you define an event which annotates an existing event.*/ /** Lets you define an event which annotates an existing event.*/
const val ANNOTATION = "m.annotation" const val ANNOTATION = "m.annotation"
/** Lets you define an event which replaces an existing event.*/ /** Lets you define an event which replaces an existing event.*/
const val REPLACE = "m.replace" const val REPLACE = "m.replace"
/** Lets you define an event which references an existing event.*/ /** Lets you define an event which references an existing event.*/
const val REFERENCE = "m.reference" const val REFERENCE = "m.reference"
/** Lets you define an event which adds a response to an existing event.*/ /** Lets you define an event which adds a response to an existing event.*/
const val RESPONSE = "org.matrix.response" const val RESPONSE = "org.matrix.response"
} }

View file

@ -16,6 +16,6 @@
package org.matrix.android.sdk.api.session.events.model package org.matrix.android.sdk.api.session.events.model
interface UnsignedRelationInfo { interface UnsignedRelationInfo {
val limited : Boolean? val limited: Boolean?
val count: Int? val count: Int?
} }

View file

@ -33,10 +33,12 @@ data class IntegrationManagerConfig(
* Defined in UserAccountData * Defined in UserAccountData
*/ */
ACCOUNT, ACCOUNT,
/** /**
* Defined in Wellknown * Defined in Wellknown
*/ */
HOMESERVER, HOMESERVER,
/** /**
* Fallback value, hardcoded by the SDK * Fallback value, hardcoded by the SDK
*/ */

View file

@ -16,7 +16,7 @@
package org.matrix.android.sdk.api.session.room.members package org.matrix.android.sdk.api.session.room.members
sealed class ChangeMembershipState() { sealed class ChangeMembershipState {
object Unknown : ChangeMembershipState() object Unknown : ChangeMembershipState()
object Joining : ChangeMembershipState() object Joining : ChangeMembershipState()
data class FailedJoining(val throwable: Throwable) : ChangeMembershipState() data class FailedJoining(val throwable: Throwable) : ChangeMembershipState()

View file

@ -35,7 +35,7 @@ data class PollSummaryContent(
return votes?.size ?: 0 return votes?.size ?: 0
} }
fun voteCountForOption(optionIndex: Int) : Int { fun voteCountForOption(optionIndex: Int): Int {
return votes?.filter { it.optionIndex == optionIndex }?.count() ?: 0 return votes?.filter { it.optionIndex == optionIndex }?.count() ?: 0
} }
} }

View file

@ -33,6 +33,7 @@ data class RoomGuestAccessContent(
enum class GuestAccess(val value: String) { enum class GuestAccess(val value: String) {
@Json(name = "can_join") @Json(name = "can_join")
CanJoin("can_join"), CanJoin("can_join"),
@Json(name = "forbidden") @Json(name = "forbidden")
Forbidden("forbidden") Forbidden("forbidden")
} }

View file

@ -29,16 +29,19 @@ enum class RoomHistoryVisibility {
* participating homeserver with anyone, regardless of whether they have ever joined the room. * participating homeserver with anyone, regardless of whether they have ever joined the room.
*/ */
@Json(name = "world_readable") WORLD_READABLE, @Json(name = "world_readable") WORLD_READABLE,
/** /**
* Previous events are always accessible to newly joined members. All events in the * Previous events are always accessible to newly joined members. All events in the
* room are accessible, even those sent when the member was not a part of the room. * room are accessible, even those sent when the member was not a part of the room.
*/ */
@Json(name = "shared") SHARED, @Json(name = "shared") SHARED,
/** /**
* Events are accessible to newly joined members from the point they were invited onwards. * Events are accessible to newly joined members from the point they were invited onwards.
* Events stop being accessible when the member's state changes to something other than invite or join. * Events stop being accessible when the member's state changes to something other than invite or join.
*/ */
@Json(name = "invited") INVITED, @Json(name = "invited") INVITED,
/** /**
* Events are accessible to newly joined members from the point they joined the room onwards. * Events are accessible to newly joined members from the point they joined the room onwards.
* Events stop being accessible when the member's state changes to something other than join. * Events stop being accessible when the member's state changes to something other than join.

View file

@ -53,6 +53,6 @@ data class MessageAudioContent(
@Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null @Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null
) : MessageWithAttachmentContent { ) : MessageWithAttachmentContent {
override val mimeType: String? override val mimeType: String?
get() = encryptedFileInfo?.mimetype ?: audioInfo?.mimeType get() = encryptedFileInfo?.mimetype ?: audioInfo?.mimeType
} }

View file

@ -53,6 +53,6 @@ data class MessageImageContent(
*/ */
@Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null @Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null
) : MessageImageInfoContent { ) : MessageImageInfoContent {
override val mimeType: String? override val mimeType: String?
get() = encryptedFileInfo?.mimetype ?: info?.mimeType ?: "image/*" get() = encryptedFileInfo?.mimetype ?: info?.mimeType ?: "image/*"
} }

View file

@ -53,6 +53,6 @@ data class MessageStickerContent(
*/ */
@Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null @Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null
) : MessageImageInfoContent { ) : MessageImageInfoContent {
override val mimeType: String? override val mimeType: String?
get() = encryptedFileInfo?.mimetype ?: info?.mimeType get() = encryptedFileInfo?.mimetype ?: info?.mimeType
} }

View file

@ -29,6 +29,7 @@ object MessageType {
const val MSGTYPE_RESPONSE = "org.matrix.response" const val MSGTYPE_RESPONSE = "org.matrix.response"
const val MSGTYPE_POLL_CLOSED = "org.matrix.poll_closed" const val MSGTYPE_POLL_CLOSED = "org.matrix.poll_closed"
const val MSGTYPE_VERIFICATION_REQUEST = "m.key.verification.request" const val MSGTYPE_VERIFICATION_REQUEST = "m.key.verification.request"
// Add, in local, a fake message type in order to StickerMessage can inherit Message class // Add, in local, a fake message type in order to StickerMessage can inherit Message class
// Because sticker isn't a message type but a event type without msgtype field // Because sticker isn't a message type but a event type without msgtype field
const val MSGTYPE_STICKER_LOCAL = "org.matrix.android.sdk.sticker" const val MSGTYPE_STICKER_LOCAL = "org.matrix.android.sdk.sticker"

View file

@ -52,6 +52,6 @@ data class MessageVideoContent(
*/ */
@Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null @Json(name = "file") override val encryptedFileInfo: EncryptedFileInfo? = null
) : MessageWithAttachmentContent { ) : MessageWithAttachmentContent {
override val mimeType: String? override val mimeType: String?
get() = encryptedFileInfo?.mimetype ?: videoInfo?.mimeType get() = encryptedFileInfo?.mimetype ?: videoInfo?.mimeType
} }

View file

@ -18,18 +18,25 @@ package org.matrix.android.sdk.api.session.room.send
enum class SendState { enum class SendState {
UNKNOWN, UNKNOWN,
// the event has not been sent // the event has not been sent
UNSENT, UNSENT,
// the event is encrypting // the event is encrypting
ENCRYPTING, ENCRYPTING,
// the event is currently sending // the event is currently sending
SENDING, SENDING,
// the event has been sent // the event has been sent
SENT, SENT,
// the event has been received from server // the event has been received from server
SYNCED, SYNCED,
// The event failed to be sent // The event failed to be sent
UNDELIVERED, UNDELIVERED,
// the event failed to be sent because some unknown devices have been found while encrypting it // the event failed to be sent because some unknown devices have been found while encrypting it
FAILED_UNKNOWN_DEVICES; FAILED_UNKNOWN_DEVICES;

View file

@ -128,6 +128,7 @@ interface Timeline {
* It represents future events. * It represents future events.
*/ */
FORWARDS, FORWARDS,
/** /**
* It represents past events. * It represents past events.
*/ */

View file

@ -40,5 +40,5 @@ interface TimelineService {
fun getTimeLineEventLive(eventId: String): LiveData<Optional<TimelineEvent>> fun getTimeLineEventLive(eventId: String): LiveData<Optional<TimelineEvent>>
fun getAttachmentMessages() : List<TimelineEvent> fun getAttachmentMessages(): List<TimelineEvent>
} }

View file

@ -20,6 +20,7 @@ interface FilterService {
enum class FilterPreset { enum class FilterPreset {
NoFilter, NoFilter,
/** /**
* Filter for Riot, will include only known event type * Filter for Riot, will include only known event type
*/ */

View file

@ -46,7 +46,7 @@ data class Optional<T : Any> constructor(private val value: T?) {
return Optional(value) return Optional(value)
} }
fun <T: Any> empty(): Optional<T> { fun <T : Any> empty(): Optional<T> {
return Optional(null) return Optional(null)
} }
} }

View file

@ -35,6 +35,7 @@ const val MXCRYPTO_ALGORITHM_MEGOLM_BACKUP = "m.megolm_backup.v1.curve25519-aes-
* Secured Shared Storage algorithm constant * Secured Shared Storage algorithm constant
*/ */
const val SSSS_ALGORITHM_CURVE25519_AES_SHA2 = "m.secret_storage.v1.curve25519-aes-sha2" const val SSSS_ALGORITHM_CURVE25519_AES_SHA2 = "m.secret_storage.v1.curve25519-aes-sha2"
/* Secrets are encrypted using AES-CTR-256 and MACed using HMAC-SHA-256. **/ /* Secrets are encrypted using AES-CTR-256 and MACed using HMAC-SHA-256. **/
const val SSSS_ALGORITHM_AES_HMAC_SHA2 = "m.secret_storage.v1.aes-hmac-sha2" const val SSSS_ALGORITHM_AES_HMAC_SHA2 = "m.secret_storage.v1.aes-hmac-sha2"

View file

@ -28,7 +28,8 @@ enum class GossipingRequestState {
ACCEPTING, ACCEPTING,
ACCEPTED, ACCEPTED,
FAILED_TO_ACCEPTED, FAILED_TO_ACCEPTED,
// USER_REJECTED,
// USER_REJECTED,
UNABLE_TO_PROCESS, UNABLE_TO_PROCESS,
CANCELLED_BY_REQUESTER, CANCELLED_BY_REQUESTER,
RE_REQUESTED RE_REQUESTED

View file

@ -36,6 +36,7 @@ import kotlin.math.min
object MXMegolmExportEncryption { object MXMegolmExportEncryption {
private const val HEADER_LINE = "-----BEGIN MEGOLM SESSION DATA-----" private const val HEADER_LINE = "-----BEGIN MEGOLM SESSION DATA-----"
private const val TRAILER_LINE = "-----END MEGOLM SESSION DATA-----" private const val TRAILER_LINE = "-----END MEGOLM SESSION DATA-----"
// we split into lines before base64ing, because encodeBase64 doesn't deal // we split into lines before base64ing, because encodeBase64 doesn't deal
// terribly well with large arrays. // terribly well with large arrays.
private const val LINE_LENGTH = 72 * 4 / 3 private const val LINE_LENGTH = 72 * 4 / 3

View file

@ -70,7 +70,9 @@ internal class OutgoingGossipingRequestManager @Inject constructor(
delay(1500) delay(1500)
cryptoStore.getOrAddOutgoingSecretShareRequest(secretName, recipients)?.let { cryptoStore.getOrAddOutgoingSecretShareRequest(secretName, recipients)?.let {
// TODO check if there is already one that is being sent? // TODO check if there is already one that is being sent?
if (it.state == OutgoingGossipingRequestState.SENDING /**|| it.state == OutgoingGossipingRequestState.SENT*/) { if (it.state == OutgoingGossipingRequestState.SENDING
/**|| it.state == OutgoingGossipingRequestState.SENT*/
) {
Timber.v("## CRYPTO - GOSSIP sendSecretShareRequest() : we are already sending for that session: $it") Timber.v("## CRYPTO - GOSSIP sendSecretShareRequest() : we are already sending for that session: $it")
return@launch return@launch
} }

View file

@ -68,7 +68,7 @@ internal interface IMXDecrypting {
*/ */
fun shareKeysWithDevice(request: IncomingRoomKeyRequest) {} fun shareKeysWithDevice(request: IncomingRoomKeyRequest) {}
fun shareSecretWithDevice(request: IncomingSecretShareRequest, secretValue : String) {} fun shareSecretWithDevice(request: IncomingSecretShareRequest, secretValue: String) {}
fun requestKeysForEvent(event: Event, withHeld: Boolean) fun requestKeysForEvent(event: Event, withHeld: Boolean)
} }

View file

@ -104,7 +104,7 @@ internal class MXMegolmDecryption(private val userId: String,
senderCurve25519Key = olmDecryptionResult.senderKey, senderCurve25519Key = olmDecryptionResult.senderKey,
claimedEd25519Key = olmDecryptionResult.keysClaimed?.get("ed25519"), claimedEd25519Key = olmDecryptionResult.keysClaimed?.get("ed25519"),
forwardingCurve25519KeyChain = olmDecryptionResult.forwardingCurve25519KeyChain forwardingCurve25519KeyChain = olmDecryptionResult.forwardingCurve25519KeyChain
.orEmpty() .orEmpty()
) )
} else { } else {
throw MXCryptoError.Base(MXCryptoError.ErrorType.MISSING_FIELDS, MXCryptoError.MISSING_FIELDS_REASON) throw MXCryptoError.Base(MXCryptoError.ErrorType.MISSING_FIELDS, MXCryptoError.MISSING_FIELDS_REASON)

View file

@ -43,7 +43,7 @@ internal class ShieldTrustUpdater @Inject constructor(
private val taskExecutor: TaskExecutor, private val taskExecutor: TaskExecutor,
@SessionDatabase private val sessionRealmConfiguration: RealmConfiguration, @SessionDatabase private val sessionRealmConfiguration: RealmConfiguration,
private val roomSummaryUpdater: RoomSummaryUpdater private val roomSummaryUpdater: RoomSummaryUpdater
): SessionLifecycleObserver { ) : SessionLifecycleObserver {
companion object { companion object {
private val BACKGROUND_HANDLER = createBackgroundHandler("SHIELD_CRYPTO_DB_THREAD") private val BACKGROUND_HANDLER = createBackgroundHandler("SHIELD_CRYPTO_DB_THREAD")

View file

@ -80,6 +80,7 @@ class OlmInboundGroupSessionWrapper2 : Serializable {
constructor() { constructor() {
// empty // empty
} }
/** /**
* Create a new instance from the provided keys map. * Create a new instance from the provided keys map.
* *

View file

@ -66,19 +66,23 @@ enum class WithHeldCode(val value: String) {
* the user/device was blacklisted * the user/device was blacklisted
*/ */
BLACKLISTED("m.blacklisted"), BLACKLISTED("m.blacklisted"),
/** /**
* the user/devices is unverified * the user/devices is unverified
*/ */
UNVERIFIED("m.unverified"), UNVERIFIED("m.unverified"),
/** /**
* the user/device is not allowed have the key. For example, this would usually be sent in response * the user/device is not allowed have the key. For example, this would usually be sent in response
* to a key request if the user was not in the room when the message was sent * to a key request if the user was not in the room when the message was sent
*/ */
UNAUTHORISED("m.unauthorised"), UNAUTHORISED("m.unauthorised"),
/** /**
* Sent in reply to a key request if the device that the key is requested from does not have the requested key * Sent in reply to a key request if the device that the key is requested from does not have the requested key
*/ */
UNAVAILABLE("m.unavailable"), UNAVAILABLE("m.unavailable"),
/** /**
* An olm session could not be established. * An olm session could not be established.
* This may happen, for example, if the sender was unable to obtain a one-time key from the recipient. * This may happen, for example, if the sender was unable to obtain a one-time key from the recipient.

View file

@ -17,6 +17,6 @@
package org.matrix.android.sdk.internal.crypto.store package org.matrix.android.sdk.internal.crypto.store
data class SavedKeyBackupKeyInfo( data class SavedKeyBackupKeyInfo(
val recoveryKey : String, val recoveryKey: String,
val version: String val version: String
) )

View file

@ -26,10 +26,10 @@ internal fun OlmSessionEntity.Companion.createPrimaryKey(sessionId: String, devi
// olmSessionData is a serialized OlmSession // olmSessionData is a serialized OlmSession
internal open class OlmSessionEntity(@PrimaryKey var primaryKey: String = "", internal open class OlmSessionEntity(@PrimaryKey var primaryKey: String = "",
var sessionId: String? = null, var sessionId: String? = null,
var deviceKey: String? = null, var deviceKey: String? = null,
var olmSessionData: String? = null, var olmSessionData: String? = null,
var lastReceivedMessageTs: Long = 0) var lastReceivedMessageTs: Long = 0)
: RealmObject() { : RealmObject() {
fun getOlmSession(): OlmSession? { fun getOlmSession(): OlmSession? {

View file

@ -138,7 +138,7 @@ internal class DefaultOutgoingSASDefaultVerificationTransaction(
override fun onVerificationAccept(accept: ValidVerificationInfoAccept) { override fun onVerificationAccept(accept: ValidVerificationInfoAccept) {
Timber.v("## SAS O: onVerificationAccept id:$transactionId") Timber.v("## SAS O: onVerificationAccept id:$transactionId")
if (state != VerificationTxState.Started && state != VerificationTxState.SendingStart) { if (state != VerificationTxState.Started && state != VerificationTxState.SendingStart) {
Timber.e("## SAS O: received accept request from invalid state $state") Timber.e("## SAS O: received accept request from invalid state $state")
cancel(CancelCode.UnexpectedMessage) cancel(CancelCode.UnexpectedMessage)
return return
@ -212,7 +212,7 @@ internal class DefaultOutgoingSASDefaultVerificationTransaction(
// - the Matrix ID of the user who sent the m.key.verification.accept message, // - the Matrix ID of the user who sent the m.key.verification.accept message,
// - he device ID of the device that sent the m.key.verification.accept message // - he device ID of the device that sent the m.key.verification.accept message
// - the transaction ID. // - the transaction ID.
val sasInfo = "MATRIX_KEY_VERIFICATION_SAS$userId$deviceId$otherUserId$otherDeviceId$transactionId" val sasInfo = "MATRIX_KEY_VERIFICATION_SAS$userId$deviceId$otherUserId$otherDeviceId$transactionId"
// decimal: generate five bytes by using HKDF. // decimal: generate five bytes by using HKDF.
// emoji: generate six bytes by using HKDF. // emoji: generate six bytes by using HKDF.
@ -220,7 +220,7 @@ internal class DefaultOutgoingSASDefaultVerificationTransaction(
} }
KEY_AGREEMENT_V2 -> { KEY_AGREEMENT_V2 -> {
// Adds the SAS public key, and separate by | // Adds the SAS public key, and separate by |
val sasInfo = "MATRIX_KEY_VERIFICATION_SAS|$userId|$deviceId|${getSAS().publicKey}|$otherUserId|$otherDeviceId|$otherKey|$transactionId" val sasInfo = "MATRIX_KEY_VERIFICATION_SAS|$userId|$deviceId|${getSAS().publicKey}|$otherUserId|$otherDeviceId|$otherKey|$transactionId"
return getSAS().generateShortCode(sasInfo, 6) return getSAS().generateShortCode(sasInfo, 6)
} }
else -> { else -> {

View file

@ -57,7 +57,7 @@ internal abstract class DefaultVerificationTransaction(
protected fun trust(canTrustOtherUserMasterKey: Boolean, protected fun trust(canTrustOtherUserMasterKey: Boolean,
toVerifyDeviceIds: List<String>, toVerifyDeviceIds: List<String>,
eventuallyMarkMyMasterKeyAsTrusted: Boolean, autoDone : Boolean = true) { eventuallyMarkMyMasterKeyAsTrusted: Boolean, autoDone: Boolean = true) {
Timber.d("## Verification: trust ($otherUserId,$otherDeviceId) , verifiedDevices:$toVerifyDeviceIds") Timber.d("## Verification: trust ($otherUserId,$otherDeviceId) , verifiedDevices:$toVerifyDeviceIds")
Timber.d("## Verification: trust Mark myMSK trusted $eventuallyMarkMyMasterKeyAsTrusted") Timber.d("## Verification: trust Mark myMSK trusted $eventuallyMarkMyMasterKeyAsTrusted")

View file

@ -68,10 +68,13 @@ internal abstract class SASDefaultVerificationTransaction(
// Deprecated maybe removed later, use V2 // Deprecated maybe removed later, use V2
const val KEY_AGREEMENT_V1 = "curve25519" const val KEY_AGREEMENT_V1 = "curve25519"
const val KEY_AGREEMENT_V2 = "curve25519-hkdf-sha256" const val KEY_AGREEMENT_V2 = "curve25519-hkdf-sha256"
// ordered by preferred order // ordered by preferred order
val KNOWN_AGREEMENT_PROTOCOLS = listOf(KEY_AGREEMENT_V2, KEY_AGREEMENT_V1) val KNOWN_AGREEMENT_PROTOCOLS = listOf(KEY_AGREEMENT_V2, KEY_AGREEMENT_V1)
// ordered by preferred order // ordered by preferred order
val KNOWN_HASHES = listOf("sha256") val KNOWN_HASHES = listOf("sha256")
// ordered by preferred order // ordered by preferred order
val KNOWN_MACS = listOf(SAS_MAC_SHA256, SAS_MAC_SHA256_LONGKDF) val KNOWN_MACS = listOf(SAS_MAC_SHA256, SAS_MAC_SHA256_LONGKDF)
@ -101,6 +104,7 @@ internal abstract class SASDefaultVerificationTransaction(
// Visible for test // Visible for test
var startReq: ValidVerificationInfoStart.SasVerificationInfoStart? = null var startReq: ValidVerificationInfoStart.SasVerificationInfoStart? = null
// Visible for test // Visible for test
var accepted: ValidVerificationInfoAccept? = null var accepted: ValidVerificationInfoAccept? = null
protected var otherKey: String? = null protected var otherKey: String? = null

View file

@ -118,7 +118,7 @@ internal class VerificationTransportRoomMessage(
?.firstOrNull { it.id == enqueueInfo.second } ?.firstOrNull { it.id == enqueueInfo.second }
?.let { wInfo -> ?.let { wInfo ->
when (wInfo.state) { when (wInfo.state) {
WorkInfo.State.FAILED -> { WorkInfo.State.FAILED -> {
tx?.cancel(onErrorReason) tx?.cancel(onErrorReason)
workLiveData.removeObserver(this) workLiveData.removeObserver(this)
} }
@ -135,7 +135,7 @@ internal class VerificationTransportRoomMessage(
} }
workLiveData.removeObserver(this) workLiveData.removeObserver(this)
} }
else -> { else -> {
// nop // nop
} }
} }

View file

@ -93,7 +93,7 @@ internal class RealmKeysUtils @Inject constructor(context: Context,
} }
// Expose to handle Realm migration to riotX // Expose to handle Realm migration to riotX
fun getRealmEncryptionKey(alias: String) : ByteArray { fun getRealmEncryptionKey(alias: String): ByteArray {
val key = if (hasKeyForDatabase(alias)) { val key = if (hasKeyForDatabase(alias)) {
Timber.i("Found key for alias:$alias") Timber.i("Found key for alias:$alias")
extractKeyForDatabase(alias) extractKeyForDatabase(alias)

View file

@ -28,8 +28,8 @@ import kotlinx.coroutines.withContext
import kotlinx.coroutines.withTimeout import kotlinx.coroutines.withTimeout
internal suspend fun <T> awaitNotEmptyResult(realmConfiguration: RealmConfiguration, internal suspend fun <T> awaitNotEmptyResult(realmConfiguration: RealmConfiguration,
timeoutMillis: Long, timeoutMillis: Long,
builder: (Realm) -> RealmQuery<T>) { builder: (Realm) -> RealmQuery<T>) {
withTimeout(timeoutMillis) { withTimeout(timeoutMillis) {
// Confine Realm interaction to a single thread with Looper. // Confine Realm interaction to a single thread with Looper.
withContext(Dispatchers.Main) { withContext(Dispatchers.Main) {

View file

@ -23,12 +23,12 @@ import io.realm.annotations.Index
import io.realm.annotations.LinkingObjects import io.realm.annotations.LinkingObjects
internal open class ChunkEntity(@Index var prevToken: String? = null, internal open class ChunkEntity(@Index var prevToken: String? = null,
// Because of gaps we can have several chunks with nextToken == null // Because of gaps we can have several chunks with nextToken == null
@Index var nextToken: String? = null, @Index var nextToken: String? = null,
var stateEvents: RealmList<EventEntity> = RealmList(), var stateEvents: RealmList<EventEntity> = RealmList(),
var timelineEvents: RealmList<TimelineEventEntity> = RealmList(), var timelineEvents: RealmList<TimelineEventEntity> = RealmList(),
var numberOfTimelineEvents: Long = 0, var numberOfTimelineEvents: Long = 0,
// Only one chunk will have isLastForward == true // Only one chunk will have isLastForward == true
@Index var isLastForward: Boolean = false, @Index var isLastForward: Boolean = false,
@Index var isLastBackward: Boolean = false @Index var isLastBackward: Boolean = false
) : RealmObject() { ) : RealmObject() {

View file

@ -20,5 +20,5 @@ import io.realm.RealmObject
import io.realm.annotations.PrimaryKey import io.realm.annotations.PrimaryKey
internal open class SyncEntity(var nextBatch: String? = null, internal open class SyncEntity(var nextBatch: String? = null,
@PrimaryKey var id: Long = 0 @PrimaryKey var id: Long = 0
) : RealmObject() ) : RealmObject()

View file

@ -47,6 +47,7 @@ internal fun EventAnnotationsSummaryEntity.Companion.create(realm: Realm, roomId
} }
return obj return obj
} }
internal fun EventAnnotationsSummaryEntity.Companion.getOrCreate(realm: Realm, roomId: String, eventId: String): EventAnnotationsSummaryEntity { internal fun EventAnnotationsSummaryEntity.Companion.getOrCreate(realm: Realm, roomId: String, eventId: String): EventAnnotationsSummaryEntity {
return EventAnnotationsSummaryEntity.where(realm, eventId).findFirst() return EventAnnotationsSummaryEntity.where(realm, eventId).findFirst()
?: EventAnnotationsSummaryEntity.create(realm, roomId, eventId).apply { this.roomId = roomId } ?: EventAnnotationsSummaryEntity.create(realm, roomId, eventId).apply { this.roomId = roomId }

View file

@ -181,7 +181,7 @@ public class HomeServerConnectionConfig {
if (!TextUtils.isEmpty(jitsiServerUrl)) { if (!TextUtils.isEmpty(jitsiServerUrl)) {
// add trailing "/" // add trailing "/"
if (!jitsiServerUrl.endsWith("/")) { if (!jitsiServerUrl.endsWith("/")) {
jitsiServerUrl =jitsiServerUrl + "/"; jitsiServerUrl = jitsiServerUrl + "/";
} }
Timber.d("Overriding jitsi server url to " + jitsiServerUrl); Timber.d("Overriding jitsi server url to " + jitsiServerUrl);

View file

@ -20,6 +20,6 @@ package org.matrix.android.sdk.internal.legacy.riot
*/ */
data class WellKnownManagerConfig( data class WellKnownManagerConfig(
val apiUrl : String, val apiUrl: String,
val uiUrl: String val uiUrl: String
) )

View file

@ -22,14 +22,14 @@ import retrofit2.Retrofit
import java.lang.reflect.Type import java.lang.reflect.Type
object UnitConverterFactory : Converter.Factory() { object UnitConverterFactory : Converter.Factory() {
override fun responseBodyConverter(type: Type, annotations: Array<out Annotation>, override fun responseBodyConverter(type: Type, annotations: Array<out Annotation>,
retrofit: Retrofit): Converter<ResponseBody, *>? { retrofit: Retrofit): Converter<ResponseBody, *>? {
return if (type == Unit::class.java) UnitConverter else null return if (type == Unit::class.java) UnitConverter else null
} }
private object UnitConverter : Converter<ResponseBody, Unit> { private object UnitConverter : Converter<ResponseBody, Unit> {
override fun convert(value: ResponseBody) { override fun convert(value: ResponseBody) {
value.close() value.close()
}
} }
}
} }

View file

@ -43,8 +43,8 @@ internal class DefaultGetUrlTask @Inject constructor(
override suspend fun execute(params: GetUrlTask.Params): String { override suspend fun execute(params: GetUrlTask.Params): String {
return when (params.rawCacheStrategy) { return when (params.rawCacheStrategy) {
RawCacheStrategy.NoCache -> doRequest(params.url) RawCacheStrategy.NoCache -> doRequest(params.url)
is RawCacheStrategy.TtlCache -> doRequestWithCache( is RawCacheStrategy.TtlCache -> doRequestWithCache(
params.url, params.url,
params.rawCacheStrategy.validityDurationInMillis, params.rawCacheStrategy.validityDurationInMillis,
params.rawCacheStrategy.strict params.rawCacheStrategy.strict

View file

@ -65,16 +65,16 @@ internal class ImageCompressor @Inject constructor() {
val orientation = exifInfo.getAttributeInt(ExifInterface.TAG_ORIENTATION, ExifInterface.ORIENTATION_NORMAL) val orientation = exifInfo.getAttributeInt(ExifInterface.TAG_ORIENTATION, ExifInterface.ORIENTATION_NORMAL)
val matrix = Matrix() val matrix = Matrix()
when (orientation) { when (orientation) {
ExifInterface.ORIENTATION_ROTATE_270 -> matrix.postRotate(270f) ExifInterface.ORIENTATION_ROTATE_270 -> matrix.postRotate(270f)
ExifInterface.ORIENTATION_ROTATE_180 -> matrix.postRotate(180f) ExifInterface.ORIENTATION_ROTATE_180 -> matrix.postRotate(180f)
ExifInterface.ORIENTATION_ROTATE_90 -> matrix.postRotate(90f) ExifInterface.ORIENTATION_ROTATE_90 -> matrix.postRotate(90f)
ExifInterface.ORIENTATION_FLIP_HORIZONTAL -> matrix.preScale(-1f, 1f) ExifInterface.ORIENTATION_FLIP_HORIZONTAL -> matrix.preScale(-1f, 1f)
ExifInterface.ORIENTATION_FLIP_VERTICAL -> matrix.preScale(1f, -1f) ExifInterface.ORIENTATION_FLIP_VERTICAL -> matrix.preScale(1f, -1f)
ExifInterface.ORIENTATION_TRANSPOSE -> { ExifInterface.ORIENTATION_TRANSPOSE -> {
matrix.preRotate(-90f) matrix.preRotate(-90f)
matrix.preScale(-1f, 1f) matrix.preScale(-1f, 1f)
} }
ExifInterface.ORIENTATION_TRANSVERSE -> { ExifInterface.ORIENTATION_TRANSVERSE -> {
matrix.preRotate(90f) matrix.preRotate(90f)
matrix.preScale(-1f, 1f) matrix.preScale(-1f, 1f)
} }

View file

@ -312,7 +312,7 @@ internal class UploadContentWorker(val context: Context, params: WorkerParameter
val updatedContent = when (messageContent) { val updatedContent = when (messageContent) {
is MessageImageContent -> messageContent.update(url, encryptedFileInfo, newImageAttributes) is MessageImageContent -> messageContent.update(url, encryptedFileInfo, newImageAttributes)
is MessageVideoContent -> messageContent.update(url, encryptedFileInfo, thumbnailUrl, thumbnailEncryptedFileInfo) is MessageVideoContent -> messageContent.update(url, encryptedFileInfo, thumbnailUrl, thumbnailEncryptedFileInfo)
is MessageFileContent -> messageContent.update(url, encryptedFileInfo) is MessageFileContent -> messageContent.update(url, encryptedFileInfo)
is MessageAudioContent -> messageContent.update(url, encryptedFileInfo) is MessageAudioContent -> messageContent.update(url, encryptedFileInfo)
else -> messageContent else -> messageContent
} }

View file

@ -41,7 +41,7 @@ internal class DefaultAddThreePidTask @Inject constructor(
override suspend fun execute(params: Params) { override suspend fun execute(params: Params) {
when (params.threePid) { when (params.threePid) {
is ThreePid.Email -> addEmail(params.threePid) is ThreePid.Email -> addEmail(params.threePid)
is ThreePid.Msisdn -> addMsisdn(params.threePid) is ThreePid.Msisdn -> addMsisdn(params.threePid)
} }
} }

View file

@ -108,9 +108,9 @@ internal class RoomDisplayNameResolver @Inject constructor(
} }
val otherMembersCount = otherMembersSubset.count() val otherMembersCount = otherMembersSubset.count()
name = when (otherMembersCount) { name = when (otherMembersCount) {
0 -> stringProvider.getString(R.string.room_displayname_empty_room) 0 -> stringProvider.getString(R.string.room_displayname_empty_room)
1 -> resolveRoomMemberName(otherMembersSubset[0], roomMembers) 1 -> resolveRoomMemberName(otherMembersSubset[0], roomMembers)
2 -> stringProvider.getString(R.string.room_displayname_two_members, 2 -> stringProvider.getString(R.string.room_displayname_two_members,
resolveRoomMemberName(otherMembersSubset[0], roomMembers), resolveRoomMemberName(otherMembersSubset[0], roomMembers),
resolveRoomMemberName(otherMembersSubset[1], roomMembers) resolveRoomMemberName(otherMembersSubset[1], roomMembers)
) )

View file

@ -187,7 +187,7 @@ internal class DefaultSendService @AssistedInject constructor(
localEchoRepository.updateSendState(localEcho.eventId, SendState.UNSENT) localEchoRepository.updateSendState(localEcho.eventId, SendState.UNSENT)
internalSendMedia(listOf(localEcho.root), attachmentData, true) internalSendMedia(listOf(localEcho.root), attachmentData, true)
} }
is MessageFileContent -> { is MessageFileContent -> {
val attachmentData = ContentAttachmentData( val attachmentData = ContentAttachmentData(
size = messageContent.info!!.size, size = messageContent.info!!.size,
mimeType = messageContent.info.mimeType!!, mimeType = messageContent.info.mimeType!!,

View file

@ -204,7 +204,7 @@ internal class LocalEchoEventFactory @Inject constructor(
ContentAttachmentData.Type.IMAGE -> createImageEvent(roomId, attachment) ContentAttachmentData.Type.IMAGE -> createImageEvent(roomId, attachment)
ContentAttachmentData.Type.VIDEO -> createVideoEvent(roomId, attachment) ContentAttachmentData.Type.VIDEO -> createVideoEvent(roomId, attachment)
ContentAttachmentData.Type.AUDIO -> createAudioEvent(roomId, attachment) ContentAttachmentData.Type.AUDIO -> createAudioEvent(roomId, attachment)
ContentAttachmentData.Type.FILE -> createFileEvent(roomId, attachment) ContentAttachmentData.Type.FILE -> createFileEvent(roomId, attachment)
} }
} }

View file

@ -68,8 +68,8 @@ internal class MarkdownParser @Inject constructor(
return this return this
// Remove extra space before and after the content // Remove extra space before and after the content
.trim() .trim()
// There is no need to include new line in an html-like source // There is no need to include new line in an html-like source
// But new line can be in embedded code block, so do not remove them // But new line can be in embedded code block, so do not remove them
// .replace("\n", "") // .replace("\n", "")
} }
} }

View file

@ -423,14 +423,14 @@ internal class DefaultTimeline(
private fun getState(direction: Timeline.Direction): State { private fun getState(direction: Timeline.Direction): State {
return when (direction) { return when (direction) {
Timeline.Direction.FORWARDS -> forwardsState.get() Timeline.Direction.FORWARDS -> forwardsState.get()
Timeline.Direction.BACKWARDS -> backwardsState.get() Timeline.Direction.BACKWARDS -> backwardsState.get()
} }
} }
private fun updateState(direction: Timeline.Direction, update: (State) -> State) { private fun updateState(direction: Timeline.Direction, update: (State) -> State) {
val stateReference = when (direction) { val stateReference = when (direction) {
Timeline.Direction.FORWARDS -> forwardsState Timeline.Direction.FORWARDS -> forwardsState
Timeline.Direction.BACKWARDS -> backwardsState Timeline.Direction.BACKWARDS -> backwardsState
} }
val currentValue = stateReference.get() val currentValue = stateReference.get()
@ -741,10 +741,10 @@ internal class DefaultTimeline(
return object : MatrixCallback<TokenChunkEventPersistor.Result> { return object : MatrixCallback<TokenChunkEventPersistor.Result> {
override fun onSuccess(data: TokenChunkEventPersistor.Result) { override fun onSuccess(data: TokenChunkEventPersistor.Result) {
when (data) { when (data) {
TokenChunkEventPersistor.Result.SUCCESS -> { TokenChunkEventPersistor.Result.SUCCESS -> {
Timber.v("Success fetching $limit items $direction from pagination request") Timber.v("Success fetching $limit items $direction from pagination request")
} }
TokenChunkEventPersistor.Result.REACHED_END -> { TokenChunkEventPersistor.Result.REACHED_END -> {
postSnapshot() postSnapshot()
} }
TokenChunkEventPersistor.Result.SHOULD_FETCH_MORE -> TokenChunkEventPersistor.Result.SHOULD_FETCH_MORE ->

View file

@ -58,6 +58,7 @@ internal class TimelineEventDecryptor @Inject constructor(
// Set of eventIds which are currently decrypting // Set of eventIds which are currently decrypting
private val existingRequests = mutableSetOf<DecryptionRequest>() private val existingRequests = mutableSetOf<DecryptionRequest>()
// sessionId -> list of eventIds // sessionId -> list of eventIds
private val unknownSessionsFailure = mutableMapOf<String, MutableSet<DecryptionRequest>>() private val unknownSessionsFailure = mutableMapOf<String, MutableSet<DecryptionRequest>>()

View file

@ -48,6 +48,7 @@ internal class DefaultTypingService @AssistedInject constructor(
// What the homeserver knows // What the homeserver knows
private var userIsTyping = false private var userIsTyping = false
// Last time the user is typing event has been sent // Last time the user is typing event has been sent
private var lastRequestTimestamp: Long = 0 private var lastRequestTimestamp: Long = 0

View file

@ -91,9 +91,9 @@ internal class ReadReceiptHandler @Inject constructor() {
for ((eventId, receiptDict) in content) { for ((eventId, receiptDict) in content) {
val userIdsDict = receiptDict[READ_KEY] ?: continue val userIdsDict = receiptDict[READ_KEY] ?: continue
val readReceiptsSummary = ReadReceiptsSummaryEntity.where(realm, eventId).findFirst() val readReceiptsSummary = ReadReceiptsSummaryEntity.where(realm, eventId).findFirst()
?: realm.createObject(ReadReceiptsSummaryEntity::class.java, eventId).apply { ?: realm.createObject(ReadReceiptsSummaryEntity::class.java, eventId).apply {
this.roomId = roomId this.roomId = roomId
} }
for ((userId, paramsDict) in userIdsDict) { for ((userId, paramsDict) in userIdsDict) {
val ts = paramsDict[TIMESTAMP_KEY] ?: 0.0 val ts = paramsDict[TIMESTAMP_KEY] ?: 0.0

View file

@ -33,7 +33,7 @@ internal class RoomTagHandler @Inject constructor() {
RoomTagEntity(tagName, params["order"] as? Double) RoomTagEntity(tagName, params["order"] as? Double)
} }
val roomSummaryEntity = RoomSummaryEntity.where(realm, roomId).findFirst() val roomSummaryEntity = RoomSummaryEntity.where(realm, roomId).findFirst()
?: RoomSummaryEntity(roomId) ?: RoomSummaryEntity(roomId)
roomSummaryEntity.tags.clear() roomSummaryEntity.tags.clear()
roomSummaryEntity.tags.addAll(tags) roomSummaryEntity.tags.addAll(tags)

View file

@ -67,6 +67,7 @@ internal class DefaultWidgetPostAPIMediator @Inject constructor(private val mosh
Timber.d("BRIDGE onWidgetEvent : $jsonEventData") Timber.d("BRIDGE onWidgetEvent : $jsonEventData")
try { try {
val dataAsDict = jsonAdapter.fromJson(jsonEventData) val dataAsDict = jsonAdapter.fromJson(jsonEventData)
@Suppress("UNCHECKED_CAST") @Suppress("UNCHECKED_CAST")
val eventData = (dataAsDict?.get("event.data") as? JsonDict) ?: return val eventData = (dataAsDict?.get("event.data") as? JsonDict) ?: return
onWidgetMessage(eventData) onWidgetMessage(eventData)

View file

@ -92,7 +92,6 @@
<data android:host="element" /> <data android:host="element" />
</intent-filter> </intent-filter>
</activity> </activity>
<activity android:name=".features.media.ImageMediaViewerActivity" />
<!-- Add tools:ignore="Instantiatable" for the error reported only by Buildkite :/ --> <!-- Add tools:ignore="Instantiatable" for the error reported only by Buildkite :/ -->
<activity <activity
@ -108,7 +107,6 @@
android:name=".features.settings.VectorSettingsActivity" android:name=".features.settings.VectorSettingsActivity"
android:label="@string/title_activity_settings" android:label="@string/title_activity_settings"
android:windowSoftInputMode="adjustResize" /> android:windowSoftInputMode="adjustResize" />
<activity android:name=".features.media.VideoMediaViewerActivity" />
<activity <activity
android:name=".features.crypto.keysbackup.restore.KeysBackupRestoreActivity" android:name=".features.crypto.keysbackup.restore.KeysBackupRestoreActivity"
android:label="@string/title_activity_keys_backup_setup" /> android:label="@string/title_activity_keys_backup_setup" />

View file

@ -18,8 +18,8 @@
package im.vector.app package im.vector.app
import arrow.core.Option import arrow.core.Option
import org.matrix.android.sdk.api.session.Session
import im.vector.app.core.utils.BehaviorDataSource import im.vector.app.core.utils.BehaviorDataSource
import org.matrix.android.sdk.api.session.Session
import javax.inject.Inject import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton

View file

@ -20,9 +20,6 @@ import androidx.lifecycle.Lifecycle
import androidx.lifecycle.LifecycleObserver import androidx.lifecycle.LifecycleObserver
import androidx.lifecycle.OnLifecycleEvent import androidx.lifecycle.OnLifecycleEvent
import arrow.core.Option import arrow.core.Option
import org.matrix.android.sdk.api.session.group.model.GroupSummary
import org.matrix.android.sdk.api.session.room.model.RoomSummary
import org.matrix.android.sdk.api.session.room.roomSummaryQueryParams
import im.vector.app.features.grouplist.ALL_COMMUNITIES_GROUP_ID import im.vector.app.features.grouplist.ALL_COMMUNITIES_GROUP_ID
import im.vector.app.features.grouplist.SelectedGroupDataSource import im.vector.app.features.grouplist.SelectedGroupDataSource
import im.vector.app.features.home.HomeRoomListDataSource import im.vector.app.features.home.HomeRoomListDataSource
@ -32,6 +29,9 @@ import io.reactivex.android.schedulers.AndroidSchedulers
import io.reactivex.disposables.CompositeDisposable import io.reactivex.disposables.CompositeDisposable
import io.reactivex.functions.BiFunction import io.reactivex.functions.BiFunction
import io.reactivex.rxkotlin.addTo import io.reactivex.rxkotlin.addTo
import org.matrix.android.sdk.api.session.group.model.GroupSummary
import org.matrix.android.sdk.api.session.room.model.RoomSummary
import org.matrix.android.sdk.api.session.room.roomSummaryQueryParams
import org.matrix.android.sdk.rx.rx import org.matrix.android.sdk.rx.rx
import java.util.concurrent.TimeUnit import java.util.concurrent.TimeUnit
import javax.inject.Inject import javax.inject.Inject

View file

@ -23,7 +23,7 @@ import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@Singleton @Singleton
class EmojiCompatFontProvider @Inject constructor(): FontsContractCompat.FontRequestCallback() { class EmojiCompatFontProvider @Inject constructor() : FontsContractCompat.FontRequestCallback() {
var typeface: Typeface? = null var typeface: Typeface? = null
set(value) { set(value) {

View file

@ -24,7 +24,7 @@ import javax.inject.Inject
import javax.inject.Singleton import javax.inject.Singleton
@Singleton @Singleton
class EmojiCompatWrapper @Inject constructor(private val context: Context) { class EmojiCompatWrapper @Inject constructor(private val context: Context) {
private var initialized = false private var initialized = false

View file

@ -51,9 +51,7 @@ import im.vector.app.features.invite.VectorInviteView
import im.vector.app.features.link.LinkHandlerActivity import im.vector.app.features.link.LinkHandlerActivity
import im.vector.app.features.login.LoginActivity import im.vector.app.features.login.LoginActivity
import im.vector.app.features.media.BigImageViewerActivity import im.vector.app.features.media.BigImageViewerActivity
import im.vector.app.features.media.ImageMediaViewerActivity
import im.vector.app.features.media.VectorAttachmentViewerActivity import im.vector.app.features.media.VectorAttachmentViewerActivity
import im.vector.app.features.media.VideoMediaViewerActivity
import im.vector.app.features.navigation.Navigator import im.vector.app.features.navigation.Navigator
import im.vector.app.features.permalink.PermalinkHandlerActivity import im.vector.app.features.permalink.PermalinkHandlerActivity
import im.vector.app.features.pin.PinLocker import im.vector.app.features.pin.PinLocker
@ -125,10 +123,8 @@ interface ScreenComponent {
fun inject(activity: MainActivity) fun inject(activity: MainActivity)
fun inject(activity: RoomDirectoryActivity) fun inject(activity: RoomDirectoryActivity)
fun inject(activity: BugReportActivity) fun inject(activity: BugReportActivity)
fun inject(activity: ImageMediaViewerActivity)
fun inject(activity: FilteredRoomsActivity) fun inject(activity: FilteredRoomsActivity)
fun inject(activity: CreateRoomActivity) fun inject(activity: CreateRoomActivity)
fun inject(activity: VideoMediaViewerActivity)
fun inject(activity: CreateDirectRoomActivity) fun inject(activity: CreateDirectRoomActivity)
fun inject(activity: IncomingShareActivity) fun inject(activity: IncomingShareActivity)
fun inject(activity: SoftLogoutActivity) fun inject(activity: SoftLogoutActivity)

View file

@ -72,12 +72,12 @@ class UnrecognizedCertificateDialog @Inject constructor(
* @param callback callback to fire when the user makes a decision * @param callback callback to fire when the user makes a decision
*/ */
private fun internalShow(activity: Activity, private fun internalShow(activity: Activity,
unrecognizedFingerprint: Fingerprint, unrecognizedFingerprint: Fingerprint,
existing: Boolean, existing: Boolean,
callback: Callback, callback: Callback,
userId: String?, userId: String?,
homeServerUrl: String, homeServerUrl: String,
homeServerConnectionConfigHasFingerprints: Boolean) { homeServerConnectionConfigHasFingerprints: Boolean) {
val dialogId = userId ?: homeServerUrl + unrecognizedFingerprint.displayableHexRepr val dialogId = userId ?: homeServerUrl + unrecognizedFingerprint.displayableHexRepr
if (openDialogIds.contains(dialogId)) { if (openDialogIds.contains(dialogId)) {

View file

@ -36,7 +36,7 @@ abstract class VectorEpoxyHolder : EpoxyHolder() {
protected fun <V : View> bind(id: Int): ReadOnlyProperty<VectorEpoxyHolder, V> = protected fun <V : View> bind(id: Int): ReadOnlyProperty<VectorEpoxyHolder, V> =
Lazy { holder: VectorEpoxyHolder, prop -> Lazy { holder: VectorEpoxyHolder, prop ->
holder.view.findViewById(id) as V? holder.view.findViewById(id) as V?
?: throw IllegalStateException("View ID $id for '${prop.name}' not found.") ?: throw IllegalStateException("View ID $id for '${prop.name}' not found.")
} }
/** /**

View file

@ -42,18 +42,25 @@ abstract class BottomSheetActionItem : VectorEpoxyModel<BottomSheetActionItem.Ho
@EpoxyAttribute @EpoxyAttribute
@DrawableRes @DrawableRes
var iconRes: Int = 0 var iconRes: Int = 0
@EpoxyAttribute @EpoxyAttribute
var textRes: Int = 0 var textRes: Int = 0
@EpoxyAttribute @EpoxyAttribute
var showExpand = false var showExpand = false
@EpoxyAttribute @EpoxyAttribute
var expanded = false var expanded = false
@EpoxyAttribute @EpoxyAttribute
var selected = false var selected = false
@EpoxyAttribute @EpoxyAttribute
var subMenuItem = false var subMenuItem = false
@EpoxyAttribute @EpoxyAttribute
var destructive = false var destructive = false
@EpoxyAttribute @EpoxyAttribute
lateinit var listener: View.OnClickListener lateinit var listener: View.OnClickListener

View file

@ -37,14 +37,19 @@ abstract class BottomSheetMessagePreviewItem : VectorEpoxyModel<BottomSheetMessa
@EpoxyAttribute @EpoxyAttribute
lateinit var avatarRenderer: AvatarRenderer lateinit var avatarRenderer: AvatarRenderer
@EpoxyAttribute @EpoxyAttribute
lateinit var matrixItem: MatrixItem lateinit var matrixItem: MatrixItem
@EpoxyAttribute @EpoxyAttribute
lateinit var body: CharSequence lateinit var body: CharSequence
@EpoxyAttribute @EpoxyAttribute
var time: CharSequence? = null var time: CharSequence? = null
@EpoxyAttribute @EpoxyAttribute
var movementMethod: MovementMethod? = null var movementMethod: MovementMethod? = null
@EpoxyAttribute @EpoxyAttribute
var userClicked: (() -> Unit)? = null var userClicked: (() -> Unit)? = null

View file

@ -33,10 +33,13 @@ abstract class BottomSheetQuickReactionsItem : VectorEpoxyModel<BottomSheetQuick
@EpoxyAttribute @EpoxyAttribute
lateinit var fontProvider: EmojiCompatFontProvider lateinit var fontProvider: EmojiCompatFontProvider
@EpoxyAttribute @EpoxyAttribute
lateinit var texts: List<String> lateinit var texts: List<String>
@EpoxyAttribute @EpoxyAttribute
lateinit var selecteds: List<Boolean> lateinit var selecteds: List<Boolean>
@EpoxyAttribute @EpoxyAttribute
var listener: Listener? = null var listener: Listener? = null

View file

@ -34,8 +34,10 @@ abstract class BottomSheetSendStateItem : VectorEpoxyModel<BottomSheetSendStateI
@EpoxyAttribute @EpoxyAttribute
var showProgress: Boolean = false var showProgress: Boolean = false
@EpoxyAttribute @EpoxyAttribute
lateinit var text: CharSequence lateinit var text: CharSequence
@EpoxyAttribute @EpoxyAttribute
@DrawableRes @DrawableRes
var drawableStart: Int = 0 var drawableStart: Int = 0

View file

@ -30,6 +30,7 @@ abstract class BaseProfileMatrixItem<T : ProfileMatrixItem.Holder> : VectorEpoxy
@EpoxyAttribute lateinit var avatarRenderer: AvatarRenderer @EpoxyAttribute lateinit var avatarRenderer: AvatarRenderer
@EpoxyAttribute lateinit var matrixItem: MatrixItem @EpoxyAttribute lateinit var matrixItem: MatrixItem
@EpoxyAttribute var editable: Boolean = true @EpoxyAttribute var editable: Boolean = true
@EpoxyAttribute @EpoxyAttribute
var userEncryptionTrustLevel: RoomEncryptionTrustLevel? = null var userEncryptionTrustLevel: RoomEncryptionTrustLevel? = null
@EpoxyAttribute var clickListener: View.OnClickListener? = null @EpoxyAttribute var clickListener: View.OnClickListener? = null

View file

@ -38,6 +38,7 @@ abstract class ProfileActionItem : VectorEpoxyModel<ProfileActionItem.Holder>()
@EpoxyAttribute @EpoxyAttribute
lateinit var title: String lateinit var title: String
@EpoxyAttribute @EpoxyAttribute
var subtitle: String? = null var subtitle: String? = null

View file

@ -24,7 +24,7 @@ import im.vector.app.core.epoxy.VectorEpoxyHolder
import im.vector.app.core.epoxy.VectorEpoxyModel import im.vector.app.core.epoxy.VectorEpoxyModel
@EpoxyModelClass(layout = R.layout.item_profile_section) @EpoxyModelClass(layout = R.layout.item_profile_section)
abstract class ProfileSectionItem: VectorEpoxyModel<ProfileSectionItem.Holder>() { abstract class ProfileSectionItem : VectorEpoxyModel<ProfileSectionItem.Holder>() {
@EpoxyAttribute @EpoxyAttribute
lateinit var title: String lateinit var title: String

View file

@ -55,46 +55,46 @@ class DefaultErrorFormatter @Inject constructor(
} }
is Failure.ServerError -> { is Failure.ServerError -> {
when { when {
throwable.error.code == MatrixError.M_CONSENT_NOT_GIVEN -> { throwable.error.code == MatrixError.M_CONSENT_NOT_GIVEN -> {
// Special case for terms and conditions // Special case for terms and conditions
stringProvider.getString(R.string.error_terms_not_accepted) stringProvider.getString(R.string.error_terms_not_accepted)
} }
throwable.isInvalidPassword() -> { throwable.isInvalidPassword() -> {
stringProvider.getString(R.string.auth_invalid_login_param) stringProvider.getString(R.string.auth_invalid_login_param)
} }
throwable.error.code == MatrixError.M_USER_IN_USE -> { throwable.error.code == MatrixError.M_USER_IN_USE -> {
stringProvider.getString(R.string.login_signup_error_user_in_use) stringProvider.getString(R.string.login_signup_error_user_in_use)
} }
throwable.error.code == MatrixError.M_BAD_JSON -> { throwable.error.code == MatrixError.M_BAD_JSON -> {
stringProvider.getString(R.string.login_error_bad_json) stringProvider.getString(R.string.login_error_bad_json)
} }
throwable.error.code == MatrixError.M_NOT_JSON -> { throwable.error.code == MatrixError.M_NOT_JSON -> {
stringProvider.getString(R.string.login_error_not_json) stringProvider.getString(R.string.login_error_not_json)
} }
throwable.error.code == MatrixError.M_THREEPID_DENIED -> { throwable.error.code == MatrixError.M_THREEPID_DENIED -> {
stringProvider.getString(R.string.login_error_threepid_denied) stringProvider.getString(R.string.login_error_threepid_denied)
} }
throwable.error.code == MatrixError.M_LIMIT_EXCEEDED -> { throwable.error.code == MatrixError.M_LIMIT_EXCEEDED -> {
limitExceededError(throwable.error) limitExceededError(throwable.error)
} }
throwable.error.code == MatrixError.M_THREEPID_NOT_FOUND -> { throwable.error.code == MatrixError.M_THREEPID_NOT_FOUND -> {
stringProvider.getString(R.string.login_reset_password_error_not_found) stringProvider.getString(R.string.login_reset_password_error_not_found)
} }
throwable.error.code == MatrixError.M_USER_DEACTIVATED -> { throwable.error.code == MatrixError.M_USER_DEACTIVATED -> {
stringProvider.getString(R.string.auth_invalid_login_deactivated_account) stringProvider.getString(R.string.auth_invalid_login_deactivated_account)
} }
throwable.error.code == MatrixError.M_THREEPID_IN_USE throwable.error.code == MatrixError.M_THREEPID_IN_USE
&& throwable.error.message == "Email is already in use" -> { && throwable.error.message == "Email is already in use" -> {
stringProvider.getString(R.string.account_email_already_used_error) stringProvider.getString(R.string.account_email_already_used_error)
} }
throwable.error.code == MatrixError.M_THREEPID_IN_USE throwable.error.code == MatrixError.M_THREEPID_IN_USE
&& throwable.error.message == "MSISDN is already in use" -> { && throwable.error.message == "MSISDN is already in use" -> {
stringProvider.getString(R.string.account_phone_number_already_used_error) stringProvider.getString(R.string.account_phone_number_already_used_error)
} }
throwable.error.code == MatrixError.M_THREEPID_AUTH_FAILED -> { throwable.error.code == MatrixError.M_THREEPID_AUTH_FAILED -> {
stringProvider.getString(R.string.error_threepid_auth_failed) stringProvider.getString(R.string.error_threepid_auth_failed)
} }
else -> { else -> {
throwable.error.message.takeIf { it.isNotEmpty() } throwable.error.message.takeIf { it.isNotEmpty() }
?: throwable.error.code.takeIf { it.isNotEmpty() } ?: throwable.error.code.takeIf { it.isNotEmpty() }
} }

View file

@ -20,8 +20,8 @@ import android.content.Context
import androidx.annotation.StringRes import androidx.annotation.StringRes
import androidx.core.text.HtmlCompat import androidx.core.text.HtmlCompat
import im.vector.app.R import im.vector.app.R
import org.matrix.android.sdk.api.failure.MatrixError
import me.gujun.android.span.span import me.gujun.android.span.span
import org.matrix.android.sdk.api.failure.MatrixError
class ResourceLimitErrorFormatter(private val context: Context) { class ResourceLimitErrorFormatter(private val context: Context) {

View file

@ -59,7 +59,7 @@ fun addEntryToDownloadManager(context: Context,
file: File, file: File,
mimeType: String, mimeType: String,
title: String = file.name, title: String = file.name,
description: String = file.name) : Uri? { description: String = file.name): Uri? {
try { try {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
val contentValues = ContentValues().apply { val contentValues = ContentValues().apply {
@ -71,16 +71,16 @@ fun addEntryToDownloadManager(context: Context,
return context.contentResolver.insert(MediaStore.Downloads.EXTERNAL_CONTENT_URI, contentValues) return context.contentResolver.insert(MediaStore.Downloads.EXTERNAL_CONTENT_URI, contentValues)
?.let { uri -> ?.let { uri ->
Timber.v("## addEntryToDownloadManager(): $uri") Timber.v("## addEntryToDownloadManager(): $uri")
val source = file.inputStream().source().buffer() val source = file.inputStream().source().buffer()
context.contentResolver.openOutputStream(uri)?.sink()?.buffer()?.let { sink -> context.contentResolver.openOutputStream(uri)?.sink()?.buffer()?.let { sink ->
source.use { input -> source.use { input ->
sink.use { output -> sink.use { output ->
output.writeAll(input) output.writeAll(input)
}
}
} }
}
}
uri uri
} ?: run { } ?: run {
Timber.v("## addEntryToDownloadManager(): context.contentResolver.insert failed") Timber.v("## addEntryToDownloadManager(): context.contentResolver.insert failed")
null null

View file

@ -33,8 +33,6 @@ import timber.log.Timber
import java.io.File import java.io.File
import java.io.IOException import java.io.IOException
import java.io.InputStream import java.io.InputStream
import java.lang.Exception
import java.lang.IllegalArgumentException
class VectorGlideModelLoaderFactory(private val activeSessionHolder: ActiveSessionHolder) class VectorGlideModelLoaderFactory(private val activeSessionHolder: ActiveSessionHolder)
: ModelLoaderFactory<ImageContentRenderer.Data, InputStream> { : ModelLoaderFactory<ImageContentRenderer.Data, InputStream> {
@ -118,7 +116,7 @@ class VectorGlideDataFetcher(private val activeSessionHolder: ActiveSessionHolde
url = data.url, url = data.url,
fileName = data.filename, fileName = data.filename,
elementToDecrypt = data.elementToDecrypt, elementToDecrypt = data.elementToDecrypt,
callback = object: MatrixCallback<File> { callback = object : MatrixCallback<File> {
override fun onSuccess(data: File) { override fun onSuccess(data: File) {
callback.onDataReady(data.inputStream()) callback.onDataReady(data.inputStream())
} }

View file

@ -109,7 +109,7 @@ fun analyseIntent(intent: Intent): List<ExternalIntentData> {
for (i in 0 until clipData.itemCount) { for (i in 0 until clipData.itemCount) {
val item = clipData.getItemAt(i) val item = clipData.getItemAt(i)
val mimeType = mimeTypes?.getOrElse(i) { mimeTypes[0] } val mimeType = mimeTypes?.getOrElse(i) { mimeTypes[0] }
// uris list is not a valid mimetype // uris list is not a valid mimetype
.takeUnless { it == ClipDescription.MIMETYPE_TEXT_URILIST } .takeUnless { it == ClipDescription.MIMETYPE_TEXT_URILIST }
externalIntentDataList.add(ExternalIntentData.IntentDataClipData(item, mimeType)) externalIntentDataList.add(ExternalIntentData.IntentDataClipData(item, mimeType))

View file

@ -121,7 +121,7 @@ object VectorLinkify {
remove = if (a.important) i + 1 else i remove = if (a.important) i + 1 else i
} else { } else {
when { when {
b.end <= a.end -> b.end <= a.end ->
// b is inside a -> b should be removed // b is inside a -> b should be removed
remove = i + 1 remove = i + 1
a.end - a.start > b.end - b.start -> a.end - a.start > b.end - b.start ->

View file

@ -26,11 +26,11 @@ class CheckableFrameLayout : FrameLayout, Checkable {
private var mChecked = false private var mChecked = false
constructor(context: Context) : super(context) {} constructor(context: Context) : super(context)
constructor(context: Context, attrs: AttributeSet) : super(context, attrs) {} constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr) {} constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) : super(context, attrs, defStyleAttr)
override fun isChecked(): Boolean { override fun isChecked(): Boolean {
return mChecked return mChecked

View file

@ -25,8 +25,8 @@ import butterknife.BindView
import im.vector.app.R import im.vector.app.R
import im.vector.app.core.di.ScreenComponent import im.vector.app.core.di.ScreenComponent
import im.vector.app.core.extensions.hideKeyboard import im.vector.app.core.extensions.hideKeyboard
import org.matrix.android.sdk.api.session.Session
import kotlinx.android.synthetic.main.activity.* import kotlinx.android.synthetic.main.activity.*
import org.matrix.android.sdk.api.session.Session
import javax.inject.Inject import javax.inject.Inject
/** /**

View file

@ -177,7 +177,7 @@ abstract class VectorBaseActivity : AppCompatActivity(), HasScreenInjector {
} }
override fun onCreate(savedInstanceState: Bundle?) { override fun onCreate(savedInstanceState: Bundle?) {
Timber.i("onCreate Activity ${this.javaClass.simpleName}") Timber.i("onCreate Activity ${javaClass.simpleName}")
val vectorComponent = getVectorComponent() val vectorComponent = getVectorComponent()
screenComponent = DaggerScreenComponent.factory().create(vectorComponent, this) screenComponent = DaggerScreenComponent.factory().create(vectorComponent, this)
val timeForInjection = measureTimeMillis { val timeForInjection = measureTimeMillis {
@ -305,7 +305,7 @@ abstract class VectorBaseActivity : AppCompatActivity(), HasScreenInjector {
override fun onDestroy() { override fun onDestroy() {
super.onDestroy() super.onDestroy()
Timber.i("onDestroy Activity ${this.javaClass.simpleName}") Timber.i("onDestroy Activity ${javaClass.simpleName}")
unBinder?.unbind() unBinder?.unbind()
unBinder = null unBinder = null
@ -333,7 +333,7 @@ abstract class VectorBaseActivity : AppCompatActivity(), HasScreenInjector {
override fun onResume() { override fun onResume() {
super.onResume() super.onResume()
Timber.i("onResume Activity ${this.javaClass.simpleName}") Timber.i("onResume Activity ${javaClass.simpleName}")
configurationViewModel.onActivityResumed() configurationViewModel.onActivityResumed()
@ -373,7 +373,7 @@ abstract class VectorBaseActivity : AppCompatActivity(), HasScreenInjector {
override fun onPause() { override fun onPause() {
super.onPause() super.onPause()
Timber.i("onPause Activity ${this.javaClass.simpleName}") Timber.i("onPause Activity ${javaClass.simpleName}")
rageShake.stop() rageShake.stop()

View file

@ -96,7 +96,7 @@ abstract class VectorBaseBottomSheetDialogFragment : BottomSheetDialogFragment()
} }
} }
var resultListener : ResultListener? = null var resultListener: ResultListener? = null
var bottomSheetResult: Int = ResultListener.RESULT_CANCEL var bottomSheetResult: Int = ResultListener.RESULT_CANCEL
var bottomSheetResultData: Any? = null var bottomSheetResultData: Any? = null
@ -141,7 +141,7 @@ abstract class VectorBaseBottomSheetDialogFragment : BottomSheetDialogFragment()
override fun onResume() { override fun onResume() {
super.onResume() super.onResume()
Timber.i("onResume BottomSheet ${this.javaClass.simpleName}") Timber.i("onResume BottomSheet ${javaClass.simpleName}")
} }
override fun onCreateDialog(savedInstanceState: Bundle?): Dialog { override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {

View file

@ -58,7 +58,7 @@ abstract class VectorBaseFragment : BaseMvRxFragment(), HasScreenInjector {
// Butterknife unbinder // Butterknife unbinder
private var mUnBinder: Unbinder? = null private var mUnBinder: Unbinder? = null
val vectorBaseActivity: VectorBaseActivity by lazy { protected val vectorBaseActivity: VectorBaseActivity by lazy {
activity as VectorBaseActivity activity as VectorBaseActivity
} }
@ -112,7 +112,7 @@ abstract class VectorBaseFragment : BaseMvRxFragment(), HasScreenInjector {
} }
final override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? { final override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
Timber.i("onCreateView Fragment ${this.javaClass.simpleName}") Timber.i("onCreateView Fragment ${javaClass.simpleName}")
return inflater.inflate(getLayoutResId(), container, false) return inflater.inflate(getLayoutResId(), container, false)
} }
@ -122,7 +122,7 @@ abstract class VectorBaseFragment : BaseMvRxFragment(), HasScreenInjector {
@CallSuper @CallSuper
override fun onResume() { override fun onResume() {
super.onResume() super.onResume()
Timber.i("onResume Fragment ${this.javaClass.simpleName}") Timber.i("onResume Fragment ${javaClass.simpleName}")
} }
@CallSuper @CallSuper
@ -142,7 +142,7 @@ abstract class VectorBaseFragment : BaseMvRxFragment(), HasScreenInjector {
@CallSuper @CallSuper
override fun onDestroyView() { override fun onDestroyView() {
super.onDestroyView() super.onDestroyView()
Timber.i("onDestroyView Fragment ${this.javaClass.simpleName}") Timber.i("onDestroyView Fragment ${javaClass.simpleName}")
mUnBinder?.unbind() mUnBinder?.unbind()
mUnBinder = null mUnBinder = null
uiDisposables.clear() uiDisposables.clear()

View file

@ -29,6 +29,7 @@ class DrawableProvider @Inject constructor(private val context: Context) {
fun getDrawable(@DrawableRes colorRes: Int): Drawable? { fun getDrawable(@DrawableRes colorRes: Int): Drawable? {
return ContextCompat.getDrawable(context, colorRes) return ContextCompat.getDrawable(context, colorRes)
} }
fun getDrawable(@DrawableRes colorRes: Int, @ColorInt color: Int): Drawable? { fun getDrawable(@DrawableRes colorRes: Int, @ColorInt color: Int): Drawable? {
return ContextCompat.getDrawable(context, colorRes)?.let { return ContextCompat.getDrawable(context, colorRes)?.let {
ThemeUtils.tintDrawableWithColor(it, color) ThemeUtils.tintDrawableWithColor(it, color)

View file

@ -28,11 +28,11 @@ import im.vector.app.R
import im.vector.app.core.error.ResourceLimitErrorFormatter import im.vector.app.core.error.ResourceLimitErrorFormatter
import im.vector.app.core.utils.DimensionConverter import im.vector.app.core.utils.DimensionConverter
import im.vector.app.features.themes.ThemeUtils import im.vector.app.features.themes.ThemeUtils
import org.matrix.android.sdk.api.failure.MatrixError
import org.matrix.android.sdk.api.session.events.model.Event
import kotlinx.android.synthetic.main.view_notification_area.view.* import kotlinx.android.synthetic.main.view_notification_area.view.*
import me.gujun.android.span.span import me.gujun.android.span.span
import me.saket.bettermovementmethod.BetterLinkMovementMethod import me.saket.bettermovementmethod.BetterLinkMovementMethod
import org.matrix.android.sdk.api.failure.MatrixError
import org.matrix.android.sdk.api.session.events.model.Event
import timber.log.Timber import timber.log.Timber
/** /**

View file

@ -56,15 +56,19 @@ class PasswordStrengthBar @JvmOverloads constructor(
@BindColor(R.color.password_strength_bar_undefined) @BindColor(R.color.password_strength_bar_undefined)
@JvmField @JvmField
var colorBackground: Int = 0 var colorBackground: Int = 0
@BindColor(R.color.password_strength_bar_weak) @BindColor(R.color.password_strength_bar_weak)
@JvmField @JvmField
var colorWeak: Int = 0 var colorWeak: Int = 0
@BindColor(R.color.password_strength_bar_low) @BindColor(R.color.password_strength_bar_low)
@JvmField @JvmField
var colorLow: Int = 0 var colorLow: Int = 0
@BindColor(R.color.password_strength_bar_ok) @BindColor(R.color.password_strength_bar_ok)
@JvmField @JvmField
var colorOk: Int = 0 var colorOk: Int = 0
@BindColor(R.color.password_strength_bar_strong) @BindColor(R.color.password_strength_bar_strong)
@JvmField @JvmField
var colorStrong: Int = 0 var colorStrong: Int = 0

View file

@ -40,13 +40,13 @@ import androidx.core.content.getSystemService
import im.vector.app.BuildConfig import im.vector.app.BuildConfig
import im.vector.app.R import im.vector.app.R
import im.vector.app.features.notifications.NotificationUtils import im.vector.app.features.notifications.NotificationUtils
import org.matrix.android.sdk.api.extensions.tryOrNull
import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
import okio.buffer import okio.buffer
import okio.sink import okio.sink
import okio.source import okio.source
import org.matrix.android.sdk.api.extensions.tryOrNull
import timber.log.Timber import timber.log.Timber
import java.io.File import java.io.File
import java.io.FileInputStream import java.io.FileInputStream

View file

@ -22,8 +22,6 @@ import android.os.Bundle
import android.os.Parcelable import android.os.Parcelable
import androidx.appcompat.app.AlertDialog import androidx.appcompat.app.AlertDialog
import com.bumptech.glide.Glide import com.bumptech.glide.Glide
import org.matrix.android.sdk.api.MatrixCallback
import org.matrix.android.sdk.api.failure.GlobalError
import im.vector.app.R import im.vector.app.R
import im.vector.app.core.di.ActiveSessionHolder import im.vector.app.core.di.ActiveSessionHolder
import im.vector.app.core.di.ScreenComponent import im.vector.app.core.di.ScreenComponent
@ -47,6 +45,8 @@ import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.launch import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext import kotlinx.coroutines.withContext
import org.matrix.android.sdk.api.MatrixCallback
import org.matrix.android.sdk.api.failure.GlobalError
import timber.log.Timber import timber.log.Timber
import javax.inject.Inject import javax.inject.Inject

View file

@ -55,8 +55,10 @@ abstract class AttachmentPreviewItem<H : AttachmentPreviewItem.Holder> : VectorE
abstract class AttachmentMiniaturePreviewItem : AttachmentPreviewItem<AttachmentMiniaturePreviewItem.Holder>() { abstract class AttachmentMiniaturePreviewItem : AttachmentPreviewItem<AttachmentMiniaturePreviewItem.Holder>() {
@EpoxyAttribute override lateinit var attachment: ContentAttachmentData @EpoxyAttribute override lateinit var attachment: ContentAttachmentData
@EpoxyAttribute @EpoxyAttribute
var clickListener: View.OnClickListener? = null var clickListener: View.OnClickListener? = null
@EpoxyAttribute @EpoxyAttribute
var checked: Boolean = false var checked: Boolean = false

View file

@ -22,6 +22,6 @@ import im.vector.app.core.platform.VectorViewModelAction
sealed class AttachmentsPreviewAction : VectorViewModelAction { sealed class AttachmentsPreviewAction : VectorViewModelAction {
object RemoveCurrentAttachment : AttachmentsPreviewAction() object RemoveCurrentAttachment : AttachmentsPreviewAction()
data class SetCurrentAttachment(val index: Int): AttachmentsPreviewAction() data class SetCurrentAttachment(val index: Int) : AttachmentsPreviewAction()
data class UpdatePathOfCurrentAttachment(val newUri: Uri): AttachmentsPreviewAction() data class UpdatePathOfCurrentAttachment(val newUri: Uri) : AttachmentsPreviewAction()
} }

Some files were not shown because too many files have changed in this diff Show more