Add device keys to rageshakes (#2838)

This commit is contained in:
Valere
2024-05-21 10:54:16 +02:00
committed by GitHub
parent aeb776e695
commit d9466d584d
16 changed files with 198 additions and 39 deletions

View File

@@ -126,8 +126,7 @@ class AuthenticationFlowCoordinator: FlowCoordinatorProtocol {
bugReportFlowCoordinator = BugReportFlowCoordinator(parameters: .init(presentationMode: .sheet(navigationStackCoordinator),
userIndicatorController: userIndicatorController,
bugReportService: bugReportService,
userID: nil,
deviceID: nil))
userSession: nil))
bugReportFlowCoordinator?.start()
}

View File

@@ -25,8 +25,7 @@ struct BugReportFlowCoordinatorParameters {
let presentationMode: PresentationMode
let userIndicatorController: UserIndicatorControllerProtocol
let bugReportService: BugReportServiceProtocol
let userID: String?
let deviceID: String?
let userSession: UserSessionProtocol?
}
class BugReportFlowCoordinator: FlowCoordinatorProtocol {
@@ -64,8 +63,7 @@ class BugReportFlowCoordinator: FlowCoordinatorProtocol {
private func presentBugReportScreen() {
let params = BugReportScreenCoordinatorParameters(bugReportService: parameters.bugReportService,
userID: parameters.userID,
deviceID: parameters.deviceID,
userSession: parameters.userSession,
userIndicatorController: parameters.userIndicatorController,
screenshot: nil,
isModallyPresented: isModallyPresented)

View File

@@ -123,8 +123,7 @@ class SettingsFlowCoordinator: FlowCoordinatorProtocol {
bugReportFlowCoordinator = BugReportFlowCoordinator(parameters: .init(presentationMode: .push(navigationStackCoordinator),
userIndicatorController: parameters.userIndicatorController,
bugReportService: parameters.bugReportService,
userID: parameters.userSession.userID,
deviceID: parameters.userSession.deviceID))
userSession: parameters.userSession))
bugReportFlowCoordinator?.start()
case .about:
presentLegalInformationScreen()

View File

@@ -307,8 +307,7 @@ class UserSessionFlowCoordinator: FlowCoordinatorProtocol {
bugReportFlowCoordinator = BugReportFlowCoordinator(parameters: .init(presentationMode: .sheet(sidebarNavigationStackCoordinator),
userIndicatorController: ServiceLocator.shared.userIndicatorController,
bugReportService: bugReportService,
userID: userSession.userID,
deviceID: userSession.deviceID))
userSession: userSession))
bugReportFlowCoordinator?.start()
case (.feedbackScreen, .dismissedFeedbackScreen, .roomList):
break

View File

@@ -3799,6 +3799,134 @@ class ClientProxyMock: ClientProxyProtocol {
return recentConversationCounterpartsReturnValue
}
}
//MARK: - ed25519Base64
var ed25519Base64UnderlyingCallsCount = 0
var ed25519Base64CallsCount: Int {
get {
if Thread.isMainThread {
return ed25519Base64UnderlyingCallsCount
} else {
var returnValue: Int? = nil
DispatchQueue.main.sync {
returnValue = ed25519Base64UnderlyingCallsCount
}
return returnValue!
}
}
set {
if Thread.isMainThread {
ed25519Base64UnderlyingCallsCount = newValue
} else {
DispatchQueue.main.sync {
ed25519Base64UnderlyingCallsCount = newValue
}
}
}
}
var ed25519Base64Called: Bool {
return ed25519Base64CallsCount > 0
}
var ed25519Base64UnderlyingReturnValue: String?
var ed25519Base64ReturnValue: String? {
get {
if Thread.isMainThread {
return ed25519Base64UnderlyingReturnValue
} else {
var returnValue: String?? = nil
DispatchQueue.main.sync {
returnValue = ed25519Base64UnderlyingReturnValue
}
return returnValue!
}
}
set {
if Thread.isMainThread {
ed25519Base64UnderlyingReturnValue = newValue
} else {
DispatchQueue.main.sync {
ed25519Base64UnderlyingReturnValue = newValue
}
}
}
}
var ed25519Base64Closure: (() async -> String?)?
func ed25519Base64() async -> String? {
ed25519Base64CallsCount += 1
if let ed25519Base64Closure = ed25519Base64Closure {
return await ed25519Base64Closure()
} else {
return ed25519Base64ReturnValue
}
}
//MARK: - curve25519Base64
var curve25519Base64UnderlyingCallsCount = 0
var curve25519Base64CallsCount: Int {
get {
if Thread.isMainThread {
return curve25519Base64UnderlyingCallsCount
} else {
var returnValue: Int? = nil
DispatchQueue.main.sync {
returnValue = curve25519Base64UnderlyingCallsCount
}
return returnValue!
}
}
set {
if Thread.isMainThread {
curve25519Base64UnderlyingCallsCount = newValue
} else {
DispatchQueue.main.sync {
curve25519Base64UnderlyingCallsCount = newValue
}
}
}
}
var curve25519Base64Called: Bool {
return curve25519Base64CallsCount > 0
}
var curve25519Base64UnderlyingReturnValue: String?
var curve25519Base64ReturnValue: String? {
get {
if Thread.isMainThread {
return curve25519Base64UnderlyingReturnValue
} else {
var returnValue: String?? = nil
DispatchQueue.main.sync {
returnValue = curve25519Base64UnderlyingReturnValue
}
return returnValue!
}
}
set {
if Thread.isMainThread {
curve25519Base64UnderlyingReturnValue = newValue
} else {
DispatchQueue.main.sync {
curve25519Base64UnderlyingReturnValue = newValue
}
}
}
}
var curve25519Base64Closure: (() async -> String?)?
func curve25519Base64() async -> String? {
curve25519Base64CallsCount += 1
if let curve25519Base64Closure = curve25519Base64Closure {
return await curve25519Base64Closure()
} else {
return curve25519Base64ReturnValue
}
}
//MARK: - loadMediaContentForSource
var loadMediaContentForSourceThrowableError: Error?

View File

@@ -25,8 +25,7 @@ enum BugReportScreenCoordinatorAction {
struct BugReportScreenCoordinatorParameters {
let bugReportService: BugReportServiceProtocol
let userID: String?
let deviceID: String?
let userSession: UserSessionProtocol?
let userIndicatorController: UserIndicatorControllerProtocol?
let screenshot: UIImage?
@@ -47,8 +46,7 @@ final class BugReportScreenCoordinator: CoordinatorProtocol {
self.parameters = parameters
viewModel = BugReportScreenViewModel(bugReportService: parameters.bugReportService,
userID: parameters.userID,
deviceID: parameters.deviceID,
clientProxy: parameters.userSession?.clientProxy,
screenshot: parameters.screenshot,
isModallyPresented: parameters.isModallyPresented)
}

View File

@@ -21,8 +21,7 @@ typealias BugReportScreenViewModelType = StateStoreViewModel<BugReportScreenView
class BugReportScreenViewModel: BugReportScreenViewModelType, BugReportScreenViewModelProtocol {
private let bugReportService: BugReportServiceProtocol
private let userID: String?
private let deviceID: String?
private let clientProxy: ClientProxyProtocol?
private let actionsSubject: PassthroughSubject<BugReportScreenViewModelAction, Never> = .init()
// periphery:ignore - when set to nil this is automatically cancelled
@@ -33,13 +32,11 @@ class BugReportScreenViewModel: BugReportScreenViewModelType, BugReportScreenVie
}
init(bugReportService: BugReportServiceProtocol,
userID: String?,
deviceID: String?,
clientProxy: ClientProxyProtocol?,
screenshot: UIImage?,
isModallyPresented: Bool) {
self.bugReportService = bugReportService
self.userID = userID
self.deviceID = deviceID
self.clientProxy = clientProxy
let bindings = BugReportScreenViewStateBindings(reportText: "", sendingLogsEnabled: true, canContact: false)
super.init(initialViewState: BugReportScreenViewState(screenshot: screenshot,
@@ -86,8 +83,12 @@ class BugReportScreenViewModel: BugReportScreenViewModelType, BugReportScreenVie
// Continue anyway without the screenshot.
}
}
let bugReport = BugReport(userID: userID,
deviceID: deviceID,
let ed25519 = await clientProxy?.ed25519Base64()
let curve25519 = await clientProxy?.curve25519Base64()
let bugReport = BugReport(userID: clientProxy?.userID,
deviceID: clientProxy?.deviceID,
ed25519: ed25519,
curve25519: curve25519,
text: context.reportText,
includeLogs: context.sendingLogsEnabled,
canContact: context.canContact,

View File

@@ -149,18 +149,18 @@ struct BugReportScreen: View {
struct BugReport_Previews: PreviewProvider, TestablePreview {
static var previews: some View {
NavigationStack {
let clientProxy = ClientProxyMock(.init(userID: "@mock:client.com", roomSummaryProvider: RoomSummaryProviderMock(.init(state: .loaded(.mockRooms)))))
BugReportScreen(context: BugReportScreenViewModel(bugReportService: BugReportServiceMock(),
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: nil,
isModallyPresented: false).context)
.previewDisplayName("Without Screenshot")
}
NavigationStack {
let clientProxy = ClientProxyMock(.init(userID: "@mock:client.com", roomSummaryProvider: RoomSummaryProviderMock(.init(state: .loaded(.mockRooms)))))
BugReportScreen(context: BugReportScreenViewModel(bugReportService: BugReportServiceMock(),
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: Asset.Images.appLogo.image,
isModallyPresented: false).context)
.previewDisplayName("With Screenshot")

View File

@@ -127,6 +127,11 @@ class BugReportService: NSObject, BugReportServiceProtocol {
params.append(.init(key: "device_id", type: .text(value: deviceID)))
}
if let ed25519 = bugReport.ed25519, let curve25519 = bugReport.curve25519 {
let compactKeys = "curve25519:\(curve25519), ed25519:\(ed25519)"
params.append(.init(key: "device_keys", type: .text(value: compactKeys)))
}
params.append(contentsOf: defaultParams)
for label in bugReport.githubLabels {

View File

@@ -21,6 +21,8 @@ import UIKit
struct BugReport: Equatable {
let userID: String?
let deviceID: String?
let ed25519: String?
let curve25519: String?
let text: String
let includeLogs: Bool
let canContact: Bool

View File

@@ -803,6 +803,16 @@ class ClientProxy: ClientProxyProtocol {
}
}
}
// MARK: - Encryption
func ed25519Base64() async -> String? {
await client.encryption().ed25519Key()
}
func curve25519Base64() async -> String? {
await client.encryption().curve25519Key()
}
}
extension ClientProxy: MediaLoaderProtocol {

View File

@@ -174,4 +174,9 @@ protocol ClientProxyProtocol: AnyObject, MediaLoaderProtocol {
func recentlyVisitedRooms() async -> Result<[String], ClientProxyError>
func recentConversationCounterparts() async -> [UserProfileProxy]
// MARK: - Encryption Info
func ed25519Base64() async -> String?
func curve25519Base64() async -> String?
}

View File

@@ -228,9 +228,12 @@ class MockScreen: Identifiable {
return navigationStackCoordinator
case .bugReport:
let navigationStackCoordinator = NavigationStackCoordinator()
let clientProxy = ClientProxyMock(.init(userID: "@mock:client.com", roomSummaryProvider: RoomSummaryProviderMock(.init(state: .loaded(.mockRooms)))))
let userSession = MockUserSession(clientProxy: clientProxy,
mediaProvider: MockMediaProvider(),
voiceMessageMediaManager: VoiceMessageMediaManagerMock())
let coordinator = BugReportScreenCoordinator(parameters: .init(bugReportService: BugReportServiceMock(),
userID: "@mock:client.com",
deviceID: nil,
userSession: userSession,
userIndicatorController: nil,
screenshot: nil,
isModallyPresented: true))

View File

@@ -37,6 +37,8 @@ class BugReportServiceTests: XCTestCase {
func testSubmitBugReportWithMockService() async throws {
let bugReport = BugReport(userID: "@mock:client.com",
deviceID: nil,
ed25519: nil,
curve25519: nil,
text: "i cannot send message",
includeLogs: true,
canContact: false,
@@ -67,6 +69,8 @@ class BugReportServiceTests: XCTestCase {
let bugReport = BugReport(userID: "@mock:client.com",
deviceID: nil,
ed25519: nil,
curve25519: nil,
text: "i cannot send message",
includeLogs: true,
canContact: false,

View File

@@ -25,9 +25,9 @@ class BugReportViewModelTests: XCTestCase {
}
func testInitialState() {
let clientProxy = ClientProxyMock(.init(userID: "@mock.client.com"))
let viewModel = BugReportScreenViewModel(bugReportService: BugReportServiceMock(),
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: nil,
isModallyPresented: false)
let context = viewModel.context
@@ -38,9 +38,9 @@ class BugReportViewModelTests: XCTestCase {
}
func testClearScreenshot() async throws {
let clientProxy = ClientProxyMock(.init(userID: "@mock.client.com"))
let viewModel = BugReportScreenViewModel(bugReportService: BugReportServiceMock(),
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: UIImage.actions,
isModallyPresented: false)
let context = viewModel.context
@@ -50,9 +50,9 @@ class BugReportViewModelTests: XCTestCase {
}
func testAttachScreenshot() async throws {
let clientProxy = ClientProxyMock(.init(userID: "@mock.client.com"))
let viewModel = BugReportScreenViewModel(bugReportService: BugReportServiceMock(),
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: nil, isModallyPresented: false)
let context = viewModel.context
XCTAssertNil(context.viewState.screenshot)
@@ -66,9 +66,13 @@ class BugReportViewModelTests: XCTestCase {
await Task.yield()
return .success(SubmitBugReportResponse(reportUrl: "https://test.test"))
}
let clientProxy = ClientProxyMock(.init(userID: "@mock.client.com", deviceID: "ABCDEFGH"))
clientProxy.ed25519Base64ReturnValue = "THEEDKEYKEY"
clientProxy.curve25519Base64ReturnValue = "THECURVEKEYKEY"
let viewModel = BugReportScreenViewModel(bugReportService: mockService,
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: nil, isModallyPresented: false)
let context = viewModel.context
@@ -86,7 +90,9 @@ class BugReportViewModelTests: XCTestCase {
XCTAssert(mockService.submitBugReportProgressListenerCallsCount == 1)
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.userID, "@mock.client.com")
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.deviceID, nil)
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.deviceID, "ABCDEFGH")
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.curve25519, "THECURVEKEYKEY")
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.ed25519, "THEEDKEYKEY")
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.text, "")
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.includeLogs, true)
XCTAssertEqual(mockService.submitBugReportProgressListenerReceivedArguments?.bugReport.canContact, false)
@@ -99,9 +105,10 @@ class BugReportViewModelTests: XCTestCase {
mockService.submitBugReportProgressListenerClosure = { _, _ in
.failure(.uploadFailure(TestError.testError))
}
let clientProxy = ClientProxyMock(.init(userID: "@mock.client.com"))
let viewModel = BugReportScreenViewModel(bugReportService: mockService,
userID: "@mock.client.com",
deviceID: nil,
clientProxy: clientProxy,
screenshot: nil, isModallyPresented: false)
let deferred = deferFulfillment(viewModel.actions) { action in

1
changelog.d/2550.misc Normal file
View File

@@ -0,0 +1 @@
Rageshake | Add device public curve25519 and ed25519 keys info to rageshake.