User verification state indicators (#3793)

* Introduce a `UserIdentityProxy` and have it combine upstream methods into an easy to digest  `UserIdentityVerificationState`. Use it in a dedicated `VerificationBadge` UI component

* Show a DMs counterpart verification state in the room header

* Show a warning on the room details `People` entry when there are identity verification state violations on any of the members.

* Show verification badges in the room member list

* Show a withdraw verification section on the room member details for users that have pinning violations.

* Remove the verification section from the profile screen as there's no reliable way to keep it up to date
- the underlying Rust SDK Olm Machine can be rebuilt without notice which would break any existing user identity change streams.

* Update preview test snapshots
This commit is contained in:
Stefan Ceriu
2025-02-18 08:37:34 +02:00
committed by GitHub
parent b71c93dfaa
commit f77faee981
101 changed files with 722 additions and 305 deletions
@@ -4860,13 +4860,13 @@ class ClientProxyMock: ClientProxyProtocol, @unchecked Sendable {
var userIdentityForReceivedUserID: String?
var userIdentityForReceivedInvocations: [String] = []
var userIdentityForUnderlyingReturnValue: Result<UserIdentity?, ClientProxyError>!
var userIdentityForReturnValue: Result<UserIdentity?, ClientProxyError>! {
var userIdentityForUnderlyingReturnValue: Result<UserIdentityProxyProtocol?, ClientProxyError>!
var userIdentityForReturnValue: Result<UserIdentityProxyProtocol?, ClientProxyError>! {
get {
if Thread.isMainThread {
return userIdentityForUnderlyingReturnValue
} else {
var returnValue: Result<UserIdentity?, ClientProxyError>? = nil
var returnValue: Result<UserIdentityProxyProtocol?, ClientProxyError>? = nil
DispatchQueue.main.sync {
returnValue = userIdentityForUnderlyingReturnValue
}
@@ -4884,9 +4884,9 @@ class ClientProxyMock: ClientProxyProtocol, @unchecked Sendable {
}
}
}
var userIdentityForClosure: ((String) async -> Result<UserIdentity?, ClientProxyError>)?
var userIdentityForClosure: ((String) async -> Result<UserIdentityProxyProtocol?, ClientProxyError>)?
func userIdentity(for userID: String) async -> Result<UserIdentity?, ClientProxyError> {
func userIdentity(for userID: String) async -> Result<UserIdentityProxyProtocol?, ClientProxyError> {
userIdentityForCallsCount += 1
userIdentityForReceivedUserID = userID
DispatchQueue.main.async {
@@ -16511,6 +16511,14 @@ class UserDiscoveryServiceMock: UserDiscoveryServiceProtocol, @unchecked Sendabl
}
}
}
class UserIdentityProxyMock: UserIdentityProxyProtocol, @unchecked Sendable {
var verificationState: UserIdentityVerificationState {
get { return underlyingVerificationState }
set(value) { underlyingVerificationState = value }
}
var underlyingVerificationState: UserIdentityVerificationState!
}
class UserIndicatorControllerMock: UserIndicatorControllerProtocol, @unchecked Sendable {
var window: UIWindow?
var alertInfo: AlertInfo<UUID>?
@@ -22876,6 +22876,71 @@ open class UserIdentitySDKMock: MatrixRustSDK.UserIdentity, @unchecked Sendable
fileprivate var pointer: UnsafeMutableRawPointer!
//MARK: - hasVerificationViolation
var hasVerificationViolationUnderlyingCallsCount = 0
open var hasVerificationViolationCallsCount: Int {
get {
if Thread.isMainThread {
return hasVerificationViolationUnderlyingCallsCount
} else {
var returnValue: Int? = nil
DispatchQueue.main.sync {
returnValue = hasVerificationViolationUnderlyingCallsCount
}
return returnValue!
}
}
set {
if Thread.isMainThread {
hasVerificationViolationUnderlyingCallsCount = newValue
} else {
DispatchQueue.main.sync {
hasVerificationViolationUnderlyingCallsCount = newValue
}
}
}
}
open var hasVerificationViolationCalled: Bool {
return hasVerificationViolationCallsCount > 0
}
var hasVerificationViolationUnderlyingReturnValue: Bool!
open var hasVerificationViolationReturnValue: Bool! {
get {
if Thread.isMainThread {
return hasVerificationViolationUnderlyingReturnValue
} else {
var returnValue: Bool? = nil
DispatchQueue.main.sync {
returnValue = hasVerificationViolationUnderlyingReturnValue
}
return returnValue!
}
}
set {
if Thread.isMainThread {
hasVerificationViolationUnderlyingReturnValue = newValue
} else {
DispatchQueue.main.sync {
hasVerificationViolationUnderlyingReturnValue = newValue
}
}
}
}
open var hasVerificationViolationClosure: (() -> Bool)?
open override func hasVerificationViolation() -> Bool {
hasVerificationViolationCallsCount += 1
if let hasVerificationViolationClosure = hasVerificationViolationClosure {
return hasVerificationViolationClosure()
} else {
return hasVerificationViolationReturnValue
}
}
//MARK: - isVerified
var isVerifiedUnderlyingCallsCount = 0
@@ -23046,6 +23111,71 @@ open class UserIdentitySDKMock: MatrixRustSDK.UserIdentity, @unchecked Sendable
try await pinClosure?()
}
//MARK: - wasPreviouslyVerified
var wasPreviouslyVerifiedUnderlyingCallsCount = 0
open var wasPreviouslyVerifiedCallsCount: Int {
get {
if Thread.isMainThread {
return wasPreviouslyVerifiedUnderlyingCallsCount
} else {
var returnValue: Int? = nil
DispatchQueue.main.sync {
returnValue = wasPreviouslyVerifiedUnderlyingCallsCount
}
return returnValue!
}
}
set {
if Thread.isMainThread {
wasPreviouslyVerifiedUnderlyingCallsCount = newValue
} else {
DispatchQueue.main.sync {
wasPreviouslyVerifiedUnderlyingCallsCount = newValue
}
}
}
}
open var wasPreviouslyVerifiedCalled: Bool {
return wasPreviouslyVerifiedCallsCount > 0
}
var wasPreviouslyVerifiedUnderlyingReturnValue: Bool!
open var wasPreviouslyVerifiedReturnValue: Bool! {
get {
if Thread.isMainThread {
return wasPreviouslyVerifiedUnderlyingReturnValue
} else {
var returnValue: Bool? = nil
DispatchQueue.main.sync {
returnValue = wasPreviouslyVerifiedUnderlyingReturnValue
}
return returnValue!
}
}
set {
if Thread.isMainThread {
wasPreviouslyVerifiedUnderlyingReturnValue = newValue
} else {
DispatchQueue.main.sync {
wasPreviouslyVerifiedUnderlyingReturnValue = newValue
}
}
}
}
open var wasPreviouslyVerifiedClosure: (() -> Bool)?
open override func wasPreviouslyVerified() -> Bool {
wasPreviouslyVerifiedCallsCount += 1
if let wasPreviouslyVerifiedClosure = wasPreviouslyVerifiedClosure {
return wasPreviouslyVerifiedClosure()
} else {
return wasPreviouslyVerifiedReturnValue
}
}
//MARK: - withdrawVerification
open var withdrawVerificationThrowableError: Error?