From e59dc25baa9906371a4ec193d598652e46582c4c Mon Sep 17 00:00:00 2001 From: Radoslav Penev Date: Fri, 17 Oct 2025 14:52:00 +0300 Subject: [PATCH 1/2] bugfix: fix hash creation in cross device session Fix creation of signing hash for cross device session to use hex; Also add test for verification of cross device session signing. --- .../MIRACLTrust-Sources/MIRACLTrust.swift | 9 +- .../MIRACLTrustCompatibilityTests.m | 22 ++--- .../Swift/AbortSessionIntergrationTest.swift | 7 +- .../AuthenticationIntegrationTests.swift | 9 +- ...sDeviceSessionAborterIntegrationTest.swift | 6 +- ...SessionAuthenticationIntegrationTest.swift | 10 +-- .../CrossDeviceSessionIntegrationTest.swift | 8 +- .../PushNotificationsIntegrationTest.swift | 12 +-- .../QRAuthenticationIntegrationTests.swift | 9 +- .../Swift/QuickCodeIntegrationTests.swift | 10 ++- .../Swift/SessionDetailIntegrationTests.swift | 14 ++-- .../Cases/Swift/SigningIntegrationTests.swift | 59 +++++++++---- .../UniversalLinkAuthIntegrationTests.swift | 7 +- .../Swift/VerificationIntegrationTests.swift | 24 +++--- .../Helpers/Helpers.swift | 26 ++++++ .../MIRACLTrustHelperAPI/HelperAPIModel.swift | 23 ++++- .../MIRACLTrustHelperAPI/PlatformAPI.swift | 30 ++++++- .../URLRequest+Extensions.swift | 29 +++++++ .../Helpers/PlatformAPIWrapper.swift | 83 +++++++++++++++---- 19 files changed, 285 insertions(+), 112 deletions(-) diff --git a/MIRACLTrust/MIRACLTrust-Sources/MIRACLTrust.swift b/MIRACLTrust/MIRACLTrust-Sources/MIRACLTrust.swift index a510f6d..d056eca 100644 --- a/MIRACLTrust/MIRACLTrust-Sources/MIRACLTrust.swift +++ b/MIRACLTrust/MIRACLTrust-Sources/MIRACLTrust.swift @@ -844,15 +844,8 @@ import Foundation completionHandler: @escaping CrossDeviceSigningCompletionHandler ) { do { - guard let hash = crossDeviceSession.signingHash.data(using: .utf8) else { - DispatchQueue.main.async { - completionHandler(false, SigningError.emptyMessageHash) - } - return - } - let signer = try Signer( - messageHash: hash, + messageHash: Data(hexString: crossDeviceSession.signingHash), sessionType: .crossDevice(sessionId: crossDeviceSession.sessionId), user: user, didRequestSigningPinHandler: didRequestSigningPinHandler diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Objective-C/MIRACLTrustCompatibilityTests.m b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Objective-C/MIRACLTrustCompatibilityTests.m index ea8ec24..990f04e 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Objective-C/MIRACLTrustCompatibilityTests.m +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Objective-C/MIRACLTrustCompatibilityTests.m @@ -37,7 +37,7 @@ @interface MIRACLTrustCompatibilityTests : XCTestCase @property (nonatomic, strong) CrossDeviceSessionCompatiblityCase *getCrossDeviceSessionCompatibilityCase; @property (nonatomic,strong) Configuration *configuration; -@property (nonatomic,strong) NSString *accessId; +@property (nonatomic,strong) StartSessionResult *session; @property (nonatomic,strong) NSString *activationToken; @property (nonatomic,strong) NSString *randomNumber; @@ -115,7 +115,7 @@ - (void)testVerificationConfirmationError self.userId = @"int@miracl.com"; self.api = [[PlatformAPIWrapper alloc] init]; - self.accessId = [self.api getAccessIdWithProjectId:projectId + self.session = [self.api startSessionWithProjectId:projectId projectURL:projectURL userId:nil hash:nil @@ -133,7 +133,7 @@ - (void)testVerificationConfirmationError projectId:projectId projectURL:projectURL userId:self.userId - accessId:self.accessId + accessId:self.session.accessId expiration:expirationDate]; NSNumber *sleepTime = @(expirationInSeconds.intValue + 1); sleep(sleepTime.intValue); @@ -148,7 +148,7 @@ - (void)testVerificationConfirmationError XCTAssertEqual(error.code, 3); XCTAssertEqualObjects(error.domain, @"MIRACLTrust.ActivationTokenError"); XCTAssertNotNil(errorResponse); - XCTAssertEqualObjects(errorResponse.accessId, self.accessId); + XCTAssertEqualObjects(errorResponse.accessId, self.session.accessId); XCTAssertEqualObjects(errorResponse.userId, self.userId); XCTAssertEqualObjects(errorResponse.projectId, projectId); @@ -202,13 +202,13 @@ - (void)testCompatibility NSString *clientSecret = NSProcessInfo.processInfo.environment[@"clientSecretCUV"]; self.userId = @"global@example.com"; self.api = [[PlatformAPIWrapper alloc] init]; - self.accessId = [self.api getAccessIdWithProjectId:projectId + self.session = [self.api startSessionWithProjectId:projectId projectURL:projectURL userId:nil hash:nil description:nil]; - self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.accessId]; + self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.session.accessId]; self.projectId = projectId; @@ -237,12 +237,12 @@ - (void)testCompatibility NSNumber *isAborted = dict[@"isAborted"]; XCTAssertTrue([isAborted boolValue]); - self.accessId = [self.api getAccessIdWithProjectId:projectId + self.session = [self.api startSessionWithProjectId:projectId projectURL:projectURL userId:nil hash:nil description:nil]; - self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.accessId]; + self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.session.accessId]; dict = [self.getCrossDeviceSessionCompatibilityCase getCrossDeviceSessionForQRCode:self.qrCodeURL]; XCTAssertTrue([dict[@"error"] isEqual:[NSNull null]]); @@ -268,12 +268,12 @@ - (void)testCompatibility isAborted = dict[@"isAborted"]; XCTAssertTrue([isAborted boolValue]); - self.accessId = [self.api getAccessIdWithProjectId:projectId + self.session = [self.api startSessionWithProjectId:projectId projectURL:projectURL userId:nil hash:nil description:nil]; - self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.accessId]; + self.qrCodeURL = [NSString stringWithFormat:@"https://mcl.mpin.io/mobile-login/#%@",self.session.accessId]; dict = [self.getCrossDeviceSessionCompatibilityCase getCrossDeviceSessionForQRCode:self.qrCodeURL]; XCTAssertTrue([dict[@"error"] isEqual:[NSNull null]]); @@ -285,7 +285,7 @@ - (void)testCompatibility projectId:projectId projectURL:projectURL userId:self.userId - accessId:self.accessId + accessId:self.session.accessId expiration:nil]; dict = [self.getActivationTokenCompatiblityCase getActivationTokenFrom:verificationURL]; self.activationToken = dict[@"activationToken"]; diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AbortSessionIntergrationTest.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AbortSessionIntergrationTest.swift index 516335e..f6645d7 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AbortSessionIntergrationTest.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AbortSessionIntergrationTest.swift @@ -3,7 +3,6 @@ import XCTest class AbortSessionIntegrationTests: XCTestCase { var userId = "" - var accessId = "" var sessionDetails: AuthenticationSessionDetails? @@ -37,7 +36,7 @@ class AbortSessionIntegrationTests: XCTestCase { .build() try MIRACLTrust.configure(with: XCTUnwrap(configuration)) - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: platformURLCUV)) + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: platformURLCUV)) let (response, _) = getActivationToken.getActivationToken( clientId: clientId, @@ -45,7 +44,7 @@ class AbortSessionIntegrationTests: XCTestCase { projectId: projectId, projectURL: platformURLCUV, userId: userId, - accessId: accessId + accessId: session.accessId ) activationToken = try XCTUnwrap(response?.activationToken) @@ -55,7 +54,7 @@ class AbortSessionIntegrationTests: XCTestCase { activationToken: activationToken ) - let (details, _) = sessionDetailsTestCase.getSessionDetails(qrCode: "https://mcl.mpin.io#\(accessId)") + let (details, _) = sessionDetailsTestCase.getSessionDetails(qrCode: "https://mcl.mpin.io#\(session.accessId)") sessionDetails = try XCTUnwrap(details) } diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AuthenticationIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AuthenticationIntegrationTests.swift index fccd0cb..157c020 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AuthenticationIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/AuthenticationIntegrationTests.swift @@ -7,7 +7,7 @@ class AuthenticationIntegrationTests: XCTestCase { var authentication = QRAuthenticationTestCase() var jwtAuthenticationTestCase = JWTAuthenticationTestCase() var getActivationToken = GetActivationTokenTestCase() - var accessId = "" + var session: StartSessionResult? var activationToken = "" var configuration: Configuration? @@ -32,7 +32,7 @@ class AuthenticationIntegrationTests: XCTestCase { jwtAuthenticationTestCase = JWTAuthenticationTestCase() jwtAuthenticationTestCase.pinCode = randomPIN - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) + session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)) configuration = try Configuration .Builder( @@ -49,7 +49,7 @@ class AuthenticationIntegrationTests: XCTestCase { projectId: projectId, projectURL: projectURL, userId: userId, - accessId: accessId + accessId: session!.accessId ) activationToken = try XCTUnwrap(response?.activationToken) @@ -237,7 +237,8 @@ class AuthenticationIntegrationTests: XCTestCase { assertError(current: jwtError, expected: AuthenticationError.revoked) // After three unsuccessful tries, the user is blocked and cannot authenticate anymore. - let qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId)" + let session = try XCTUnwrap(session) + let qrCode = "https://mcl.mpin.io/mobile-login/#\(session.accessId)" let (authenticationResult, authenticationError) = try authentication.authenticateUser( user: XCTUnwrap(user), qrCode: qrCode diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAborterIntegrationTest.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAborterIntegrationTest.swift index 78803fc..d34f40d 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAborterIntegrationTest.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAborterIntegrationTest.swift @@ -9,7 +9,7 @@ struct CrossDeviceSessionAborterIntegrationTest { let abortCrossDeviceSessionCase = CrossDeviceSessionAbortCase() let platformAPI = PlatformAPIWrapper() - var sessionId: String + var session: StartSessionResult var crossDeviceSession: CrossDeviceSession init() async throws { @@ -19,11 +19,11 @@ struct CrossDeviceSessionAborterIntegrationTest { try MIRACLTrust.configure(with: configuration) - sessionId = try await platformAPI.getAsyncAccessId( + session = try await platformAPI.getAsyncAccessId( projectId: projectId, projectURL: projectURL ) - let qrCode = "https://mcl.mpin.io#\(sessionId)" + let qrCode = "https://mcl.mpin.io#\(session.accessId)" crossDeviceSession = try await crossDeviceSessionCase.getCrossDeviceSessionForQRCode(qrCode: qrCode) } diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAuthenticationIntegrationTest.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAuthenticationIntegrationTest.swift index 5d62b30..a8aebd8 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAuthenticationIntegrationTest.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionAuthenticationIntegrationTest.swift @@ -18,7 +18,7 @@ struct CrossDeviceSessionAuthenticationIntegrationTest { var randomPIN = "" var user: User var crossDeviceSession: CrossDeviceSession - var accessId: String + var session: StartSessionResult init() async throws { randomPIN = CrossDeviceSessionAuthenticationIntegrationTest.makeRandomPin() @@ -32,8 +32,8 @@ struct CrossDeviceSessionAuthenticationIntegrationTest { try MIRACLTrust.configure(with: configuration) - accessId = try await platformAPI.getAsyncAccessId(projectId: projectId, projectURL: projectURL) - let qrCode = "https://mcl.mpin.io#\(accessId)" + session = try await platformAPI.getAsyncAccessId(projectId: projectId, projectURL: projectURL) + let qrCode = "https://mcl.mpin.io#\(session.accessId)" crossDeviceSession = try await crossDeviceSessionCase.getCrossDeviceSessionForQRCode(qrCode: qrCode) let activationToken = try await activationTokenCase.getActivationToken( clientId: clientId, @@ -56,7 +56,7 @@ struct CrossDeviceSessionAuthenticationIntegrationTest { @Test("Tests successful authentication with cross device session for Universal Link URL", .timeLimit(.minutes(1))) func authenticationWithUniviversalLinkURLCrossDeviceSession() async throws { - let url = try #require(URL(string: "https://mcl.mpin.io/#\(accessId)")) + let url = try #require(URL(string: "https://mcl.mpin.io/#\(session.accessId)")) let crossDeviceSession = try await crossDeviceSessionCase .getCrossDeviceSessionForUniversalLinkURL(universalLinkURL: url) let isAuthenticated = try await authenticationTestCase.authenticate( @@ -69,7 +69,7 @@ struct CrossDeviceSessionAuthenticationIntegrationTest { @Test("Tests successful authentication with cross device session for Universal Link URL", .timeLimit(.minutes(1))) func authenticationWithPushNotificationPayloadForCrossDeviceSession() async throws { - let qrCode = "https://mcl.mpin.io#\(accessId)" + let qrCode = "https://mcl.mpin.io#\(session.accessId)" let payload = [ "qrURL": qrCode ] diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionIntegrationTest.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionIntegrationTest.swift index d4cc9c1..4f4a348 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionIntegrationTest.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/CrossDeviceSessionIntegrationTest.swift @@ -21,7 +21,7 @@ struct CrossDeviceSessionIntegrationTest { ) .build() - sessionId = try await platformAPI.getAsyncAccessId(projectId: projectId, projectURL: url) + sessionId = try await platformAPI.getAsyncAccessId(projectId: projectId, projectURL: url).accessId try MIRACLTrust.configure(with: configuration) } @@ -37,7 +37,7 @@ struct CrossDeviceSessionIntegrationTest { func getCrossDeviceSessionForDifferentProject() async throws { let hash = UUID().uuidString let description = UUID().uuidString - let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description) + let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description).accessId let qrCode = "https://mcl.mpin.io#\(sessionId)" let session = try await crossDeviceSessionCase.getCrossDeviceSessionForQRCode(qrCode: qrCode) #expect(session.projectId == expectedProjectId) @@ -86,7 +86,7 @@ struct CrossDeviceSessionIntegrationTest { func getCrossDeviceSessionsUniversalLinkURLForDifferentProject() async throws { let hash = UUID().uuidString let description = UUID().uuidString - let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description) + let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description).accessId let universalLinkURL = try #require(URL(string: "https://mcl.mpin.io#\(sessionId)")) let session = try await crossDeviceSessionCase.getCrossDeviceSessionForUniversalLinkURL(universalLinkURL: universalLinkURL) @@ -124,7 +124,7 @@ struct CrossDeviceSessionIntegrationTest { func getCrossDeviceSessionsFromPushNotificationsPayloadDifferent() async throws { let hash = UUID().uuidString let description = UUID().uuidString - let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description) + let sessionId = try await platformAPI.getAsyncAccessId(projectId: expectedProjectId, projectURL: url, hash: hash, description: description).accessId let qrCode = "https://mcl.mpin.io#\(sessionId)" let payload = [ "qrURL": qrCode diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/PushNotificationsIntegrationTest.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/PushNotificationsIntegrationTest.swift index bda6629..14f83ae 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/PushNotificationsIntegrationTest.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/PushNotificationsIntegrationTest.swift @@ -34,10 +34,10 @@ class PushNotificationsIntegrationTest: XCTestCase { authentication = PushNotificationsAuthenticationTestCase() authentication.pinCode = randomPIN - let accessId = try XCTUnwrap( - api.getAccessId(projectId: projectId, projectURL: projectURL) + let session = try XCTUnwrap( + api.startSession(projectId: projectId, projectURL: projectURL) ) - qrURL = "https://mcl.mpin.io/mobile-login/#\(accessId)" + qrURL = "https://mcl.mpin.io/mobile-login/#\(session.accessId)" payload = [ "userID": userId, "projectID": projectId, @@ -56,7 +56,7 @@ class PushNotificationsIntegrationTest: XCTestCase { projectId: projectId, projectURL: projectURL, userId: userId, - accessId: accessId + accessId: session.accessId ) activationToken = try XCTUnwrap(response?.activationToken) @@ -242,8 +242,8 @@ class PushNotificationsIntegrationTest: XCTestCase { XCTAssertNil(regError) XCTAssertNotNil(user) - let differentAccessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL) - ) + let differentAccessId = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL) + ).accessId qrURL = "https://mcl.mpin.io/mobile-login/#\(differentAccessId)" payload = [ "userID": userId, diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QRAuthenticationIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QRAuthenticationIntegrationTests.swift index 7bd1fa1..66c028f 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QRAuthenticationIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QRAuthenticationIntegrationTests.swift @@ -7,7 +7,6 @@ class QRAuthenticationIntegrationTests: XCTestCase { var registration = RegistrationTestCase() var authentication = QRAuthenticationTestCase() var getActivationToken = GetActivationTokenTestCase() - var accessId = "" var qrCode = "" var activationToken = "" var configuration: Configuration? @@ -33,8 +32,8 @@ class QRAuthenticationIntegrationTests: XCTestCase { authentication = QRAuthenticationTestCase() authentication.pinCode = randomPIN - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) - qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)) + qrCode = "https://mcl.mpin.io/mobile-login/#\(session.accessId)" configuration = try Configuration .Builder( @@ -50,7 +49,7 @@ class QRAuthenticationIntegrationTests: XCTestCase { projectId: projectId, projectURL: projectURL, userId: userId, - accessId: accessId + accessId: session.accessId ) activationToken = try XCTUnwrap(response?.activationToken) @@ -141,7 +140,7 @@ class QRAuthenticationIntegrationTests: XCTestCase { XCTAssertNil(regError) XCTAssertNotNil(user) - let differentAccessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) + let differentAccessId = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)).accessId qrCode = "https://mcl.mpin.io/mobile-login/#\(differentAccessId)" let (isAuthenticated, authError) = try authentication.authenticateUser( user: XCTUnwrap(user), diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QuickCodeIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QuickCodeIntegrationTests.swift index 44fd580..c49bbd3 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QuickCodeIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/QuickCodeIntegrationTests.swift @@ -6,7 +6,7 @@ class QuickCodeIntegrationTests: XCTestCase { var authenticationTestCase = QRAuthenticationTestCase() var quickCodeTestCase = QuickCodeTestCase() var getActivationToken = GetActivationTokenTestCase() - var accessId = "" + var session: StartSessionResult? var activationToken = "" var configuration: Configuration? @@ -33,7 +33,8 @@ class QuickCodeIntegrationTests: XCTestCase { quickCodeTestCase = QuickCodeTestCase() quickCodeTestCase.authenticationPinCode = randomPIN - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) + session = api.startSession(projectId: projectId, projectURL: projectURL) + let session = try XCTUnwrap(session) configuration = try Configuration .Builder(projectId: projectId, projectURL: projectURL) @@ -49,7 +50,7 @@ class QuickCodeIntegrationTests: XCTestCase { projectId: projectId, projectURL: projectURL, userId: userId, - accessId: accessId + accessId: session.accessId ) activationToken = try XCTUnwrap(response?.activationToken) @@ -230,7 +231,8 @@ class QuickCodeIntegrationTests: XCTestCase { ) // After three unsuccessful tries, the user is blocked and cannot authenticate anymore. - let qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId)" + let session = try XCTUnwrap(session) + let qrCode = "https://mcl.mpin.io/mobile-login/#\(session.accessId)" let (authenticationResult, authenticationError) = try authenticationTestCase.authenticateUser( user: XCTUnwrap(user), qrCode: qrCode diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SessionDetailIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SessionDetailIntegrationTests.swift index 784e9c0..e421ed6 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SessionDetailIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SessionDetailIntegrationTests.swift @@ -6,7 +6,7 @@ class SessionDetailIntegrationTests: XCTestCase { let projectId = ProcessInfo.processInfo.environment["projectIdCUV"]! let testCase = SessionDetailsTestCase() - var accessId = "" + var session: StartSessionResult? var qrCode = "" var pushNotificationsPayload = [AnyHashable: Any]() var universalLinkURL: URL? @@ -17,8 +17,8 @@ class SessionDetailIntegrationTests: XCTestCase { let userId = "int@miracl.com" override func setUpWithError() throws { - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) - qrCode = "https://mcl.mpin.io#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)) + qrCode = "https://mcl.mpin.io#\(session.accessId)" universalLinkURL = URL(string: qrCode) pushNotificationsPayload = ["qrURL": qrCode] @@ -40,8 +40,8 @@ class SessionDetailIntegrationTests: XCTestCase { } func testGetSessionDetailForDifferentProject() throws { - accessId = try XCTUnwrap(api.getAccessId(projectId: expectedProjectId, projectURL: projectURL)) - qrCode = "https://mcl.mpin.io#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: expectedProjectId, projectURL: projectURL)) + qrCode = "https://mcl.mpin.io#\(session.accessId)" let (details, error) = testCase.getSessionDetails(qrCode: qrCode) XCTAssertNil(error) @@ -87,8 +87,8 @@ class SessionDetailIntegrationTests: XCTestCase { } func testGetSessionDetailsUniversalLinkURLForDifferentProject() throws { - accessId = try XCTUnwrap(api.getAccessId(projectId: expectedProjectId, projectURL: projectURL)) - qrCode = "https://mcl.mpin.io#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: expectedProjectId, projectURL: projectURL)) + qrCode = "https://mcl.mpin.io#\(session.accessId)" let universalLinkURL = try XCTUnwrap(URL(string: qrCode)) let (details, error) = testCase.getSessionDetails(universalLinkURL: universalLinkURL) diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SigningIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SigningIntegrationTests.swift index 6c0612f..6ef936d 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SigningIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/SigningIntegrationTests.swift @@ -3,11 +3,6 @@ import XCTest @testable import MIRACLTrust -extension Digest { - var bytes: [UInt8] { Array(makeIterator()) } - var data: Data { Data(bytes) } -} - class SigningIntegrationTests: XCTestCase { var registration = RegistrationTestCase() var authentication = QRAuthenticationTestCase() @@ -16,7 +11,7 @@ class SigningIntegrationTests: XCTestCase { var signingSessionDetails = GetSigningSessionDetailsTestCase() var crossDeviceSession = GetCrossDeviceSessionTestCase() - var accessId = "" + var session: StartSessionResult? var activationToken = "" var configuration: Configuration? var registeredSigningUser: User? @@ -50,7 +45,8 @@ class SigningIntegrationTests: XCTestCase { authentication = QRAuthenticationTestCase() authentication.pinCode = randomPIN - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) + session = api.startSession(projectId: projectId, projectURL: projectURL) + let session = try XCTUnwrap(session) configuration = try Configuration .Builder( @@ -78,7 +74,7 @@ class SigningIntegrationTests: XCTestCase { registeredSigningUser = try XCTUnwrap(user) XCTAssertNil(regError) - let qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId)" + let qrCode = "https://mcl.mpin.io/mobile-login/#\(session.accessId)" let (isAuthenticated, authError) = try authentication.authenticateUser( user: XCTUnwrap(user), qrCode: qrCode @@ -158,26 +154,55 @@ class SigningIntegrationTests: XCTestCase { XCTAssertTrue(isSignatureVerified) } - func testSigningCorrectnessWithCrossDeviceSession() throws { - let sessionId = try XCTUnwrap( - api.getAccessId(projectId: projectId, projectURL: projectURL, userId: userId, hash: messageToSign, description: UUID().uuidString) + func testSigningCorrectnessWithCrossDeviceSession() async throws { + let session = try XCTUnwrap( + api.startSession( + projectId: projectId, + projectURL: projectURL, + userId: userId, + hash: messageToSign.toHexString(), + description: UUID().uuidString + ) ) - let qrCode = "tcb.miracl.app/mobile/sign#\(sessionId)" + let qrCode = "tcb.miracl.app/mobile/sign#\(session.accessId)" let (crossDeviceSession, _) = crossDeviceSession.getCrossDeviceSession(qrCode: qrCode) + let crossDeviceSessionUnwrap = try XCTUnwrap(crossDeviceSession) let (signingResult, error) = try signing.signMessage( - crossDeviceSession: XCTUnwrap(crossDeviceSession), + crossDeviceSession: crossDeviceSessionUnwrap, user: XCTUnwrap(registeredSigningUser) ) XCTAssertTrue(signingResult) XCTAssertNil(error) + + let sessionStatusResult = try await api.getSessionStatus( + projectURL: projectURL, + webOTT: session.webOTT + ) + let sessionStatusResultResponse = try XCTUnwrap(sessionStatusResult.signature.fromBase64()) + let signature = try JSONDecoder().decode(Signature.self, from: sessionStatusResultResponse.data(using: .utf8)!) + XCTAssertEqual(crossDeviceSessionUnwrap.signingHash, signature.signatureHash) + + let timeInterval = TimeInterval(signature.timestamp) + let date = Date(timeIntervalSince1970: timeInterval) + + let isSignatureVerified = api.verifySignature( + signature: signature, + timestamp: date, + clientId: clientId, + clientSecret: clientSecret, + projectId: projectId, + projectURL: projectURL + ) + + XCTAssertTrue(isSignatureVerified) } func testSigningCorrectnessWithCrossDeviceSessionForUniversalLink() throws { let sessionId = try XCTUnwrap( - api.getAccessId(projectId: projectId, projectURL: projectURL, userId: userId, hash: messageToSign, description: UUID().uuidString) - ) + api.startSession(projectId: projectId, projectURL: projectURL, userId: userId, hash: messageToSign, description: UUID().uuidString) + ).accessId let universalLinkURL = try XCTUnwrap(URL(string: "https://mcl.mpin.io/mobile/sign#\(sessionId)")) let (crossDeviceSession, _) = crossDeviceSession.getCrossDeviceSession(universalLinkURL: universalLinkURL) @@ -192,8 +217,8 @@ class SigningIntegrationTests: XCTestCase { func testSigningCorrectnessWithCrossDeviceSessionForPayload() throws { let sessionId = try XCTUnwrap( - api.getAccessId(projectId: projectId, projectURL: projectURL, userId: userId, hash: messageToSign, description: UUID().uuidString) - ) + api.startSession(projectId: projectId, projectURL: projectURL, userId: userId, hash: messageToSign, description: UUID().uuidString) + ).accessId let payload = ["qrURL": "https://mcl.mpin.io/mobile/sign#\(sessionId)"] let (crossDeviceSession, _) = crossDeviceSession.getCrossDeviceSession(pushNotificationPayload: payload) diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/UniversalLinkAuthIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/UniversalLinkAuthIntegrationTests.swift index e721852..b92ce13 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/UniversalLinkAuthIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/UniversalLinkAuthIntegrationTests.swift @@ -5,7 +5,6 @@ class UniversalLinkAuthIntegrationTests: XCTestCase { var registration = RegistrationTestCase() var authentication = UniversalLinkAuthenticationTestCase() var getActivationToken = GetActivationTokenTestCase() - var accessId = "" var qrCode = "" var universalLinkURL: URL? var activationToken = "" @@ -33,8 +32,8 @@ class UniversalLinkAuthIntegrationTests: XCTestCase { authentication = UniversalLinkAuthenticationTestCase() authentication.pinCode = randomPIN - accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) - qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId)" + let accessId = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)) + qrCode = "https://mcl.mpin.io/mobile-login/#\(accessId.accessId)" universalLinkURL = URL(string: qrCode) configuration = try Configuration @@ -139,7 +138,7 @@ class UniversalLinkAuthIntegrationTests: XCTestCase { XCTAssertNil(regError) XCTAssertNotNil(user) - let differentAccessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURL)) + let differentAccessId = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURL)).accessId qrCode = "https://mcl.mpin.io/mobile-login/#\(differentAccessId)" universalLinkURL = URL(string: qrCode) let universalLinkURL = try XCTUnwrap(universalLinkURL) diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/VerificationIntegrationTests.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/VerificationIntegrationTests.swift index e7eb029..09c7040 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/VerificationIntegrationTests.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Cases/Swift/VerificationIntegrationTests.swift @@ -204,8 +204,8 @@ class VerificationIntegrationTests: XCTestCase { func testVerificationWithSessionDetails() async throws { let extendedMailAddress = "int+\(UUID().uuidString)@miracl.com" - let accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURLDV)) - let qrCode = "https://mcl.mpin.io#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURLDV)) + let qrCode = "https://mcl.mpin.io#\(session.accessId)" configuration = try Configuration .Builder(projectId: projectId, projectURL: projectURLDV) @@ -233,13 +233,13 @@ class VerificationIntegrationTests: XCTestCase { XCTAssertNil(activationTokenError) let response = try XCTUnwrap(activationTokenResponse) - XCTAssertEqual(response.accessId, accessId) + XCTAssertEqual(response.accessId, session.accessId) } func testVerificationWithCrossDeviceSessionDetails() async throws { let extendedMailAddress = "int+\(UUID().uuidString)@miracl.com" - let accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURLDV)) - let qrCode = "https://mcl.mpin.io#\(accessId)" + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURLDV)) + let qrCode = "https://mcl.mpin.io#\(session.accessId)" configuration = try Configuration .Builder(projectId: projectId, projectURL: projectURLDV) @@ -265,7 +265,7 @@ class VerificationIntegrationTests: XCTestCase { XCTAssertNil(activationTokenError) let response = try XCTUnwrap(activationTokenResponse) - XCTAssertEqual(response.accessId, accessId) + XCTAssertEqual(response.accessId, session.accessId) } func testEmailCodeVerification() async throws { @@ -455,7 +455,7 @@ class VerificationIntegrationTests: XCTestCase { func testCustomVerification() throws { let mailAddress = "int@miracl.com" - let accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURLDV)) + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURLDV)) configuration = try Configuration .Builder(projectId: projectIdPV, projectURL: projectURLPV) @@ -473,7 +473,7 @@ class VerificationIntegrationTests: XCTestCase { projectId: projectIdPV, projectURL: projectURLPV, userId: mailAddress, - accessId: accessId, + accessId: session.accessId, expiration: expirationDate ) ) @@ -492,12 +492,12 @@ class VerificationIntegrationTests: XCTestCase { XCTAssertNotNil(activationTokenResponse) XCTAssertNil(activationTokenError) XCTAssertEqual(activationTokenResponse?.projectId, projectIdPV) - XCTAssertEqual(activationTokenResponse?.accessId, accessId) + XCTAssertEqual(activationTokenResponse?.accessId, session.accessId) } func testExpiredActivationCode() throws { let mailAddress = "int@miracl.com" - let accessId = try XCTUnwrap(api.getAccessId(projectId: projectId, projectURL: projectURLDV)) + let session = try XCTUnwrap(api.startSession(projectId: projectId, projectURL: projectURLDV)) configuration = try Configuration .Builder(projectId: projectIdPV, projectURL: projectURLPV) @@ -515,7 +515,7 @@ class VerificationIntegrationTests: XCTestCase { projectId: projectIdPV, projectURL: projectURLPV, userId: mailAddress, - accessId: accessId, + accessId: session.accessId, expiration: expirationDate ) ) @@ -527,7 +527,7 @@ class VerificationIntegrationTests: XCTestCase { if let confirmationError = tokenError as? ActivationTokenError, case let ActivationTokenError.unsuccessfulVerification(activationTokenErrorResponse: response) = confirmationError { let unwrappedResponse = try XCTUnwrap(response) - XCTAssertEqual(unwrappedResponse.accessId, accessId) + XCTAssertEqual(unwrappedResponse.accessId, session.accessId) XCTAssertEqual(unwrappedResponse.projectId, projectIdPV) XCTAssertEqual(unwrappedResponse.userId, mailAddress) } else { diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/Helpers.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/Helpers.swift index ec0165b..1e64950 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/Helpers.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/Helpers.swift @@ -1,3 +1,4 @@ +import CryptoKit import XCTest public func assertError(current: Error?, expected: T) { @@ -15,3 +16,28 @@ extension Date { ) } } + +extension String { + func fromBase64() -> String? { + guard let data = Data(base64Encoded: self, options: .ignoreUnknownCharacters) else { + return nil + } + + return String(data: data, encoding: .utf8) + } + + func toBase64() -> String { + Data(utf8).base64EncodedString() + } +} + +extension String { + func toHexString() -> String { + utf8.map { String(format: "%02x", $0) }.joined() + } +} + +extension Digest { + var bytes: [UInt8] { Array(makeIterator()) } + var data: Data { Data(bytes) } +} diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/HelperAPIModel.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/HelperAPIModel.swift index 6544be0..29c37aa 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/HelperAPIModel.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/HelperAPIModel.swift @@ -26,8 +26,29 @@ struct VerifySigningRequestBody: Codable { var type = "verification" } -struct Session: Codable { +struct StartSessionResponse: Codable { var qrURL: URL + var webOTT: String +} + +struct SessionStatusRequestBody: Codable { + var webOTT: String +} + +public struct SessionStatusResponse: Codable { + var status: String + var signature: String +} + +@objcMembers +@objc public class StartSessionResult: NSObject, Codable { + public var accessId: String + public var webOTT: String + + init(accessId: String, webOTT: String) { + self.accessId = accessId + self.webOTT = webOTT + } } struct SessionRequestBody: Codable { diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/PlatformAPI.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/PlatformAPI.swift index a459d26..edbc4b0 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/PlatformAPI.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/PlatformAPI.swift @@ -13,7 +13,7 @@ import MIRACLTrust userId: String? = nil, hash: String? = nil, description: String? = nil, - completionHandler: @escaping @Sendable (String?, Error?) -> Void + completionHandler: @escaping @Sendable (StartSessionResult?, Error?) -> Void ) { guard let url = URL(string: projectURL) else { return @@ -29,13 +29,14 @@ import MIRACLTrust return } - requestExecutor.executeHTTPRequest(request: request) { (result: Result) in + requestExecutor.executeHTTPRequest(request: request) { (result: Result) in switch result { case let .success(session): if let session = session { if let urlComponents = URLComponents(url: session.qrURL, resolvingAgainstBaseURL: false) { if let fragment = urlComponents.fragment { - completionHandler(fragment, nil) + let session = StartSessionResult(accessId: fragment, webOTT: session.webOTT) + completionHandler(session, nil) } } } @@ -134,6 +135,29 @@ import MIRACLTrust task.resume() } + public func accessRequest( + projectURL: String, + webOTT: String, + completionHandler: @escaping @Sendable (SessionStatusResponse?, Error?) -> Void + ) { + guard let url = URL(string: projectURL) else { + return + } + + guard let request = URLRequest.accessRequest(url: url, webOTT: webOTT) else { + return + } + + requestExecutor.executeHTTPRequest(request: request) { (result: Result) in + switch result { + case let .success(success): + completionHandler(success, nil) + case let .failure(failure): + completionHandler(nil, failure) + } + } + } + @objc public func startSigningSession( projectID: String, projectURL: String, diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/URLRequest+Extensions.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/URLRequest+Extensions.swift index cdf8722..3787336 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/URLRequest+Extensions.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/MIRACLTrustHelperAPI/URLRequest+Extensions.swift @@ -226,6 +226,35 @@ extension URLRequest { return request } + static func accessRequest( + url: URL, + webOTT: String + ) -> URLRequest? { + guard var components = URLComponents(url: url, resolvingAgainstBaseURL: false) else { + return nil + } + + components.path = "/rps/v2/access" + + guard let url = components.url else { + return nil + } + + var request = URLRequest(url: url) + request.addValue("application/json", forHTTPHeaderField: "Content-Type") + request.httpMethod = "POST" + + let requestBody = SessionStatusRequestBody(webOTT: webOTT) + + do { + request.httpBody = try JSONEncoder().encode(requestBody) + } catch { + return nil + } + + return request + } + static func gmailAccessTokenRequest(for credentials: Credentials, refreshToken: String) -> URLRequest? { var request = URLRequest(url: URL(string: credentials.installed.tokenURI)!) request.httpMethod = "POST" diff --git a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/PlatformAPIWrapper.swift b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/PlatformAPIWrapper.swift index 01a29ca..96f30d1 100644 --- a/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/PlatformAPIWrapper.swift +++ b/MIRACLTrust/MIRACLTrustIntegrationTests/Helpers/PlatformAPIWrapper.swift @@ -53,14 +53,14 @@ import MIRACLTrust return jwkSet } - @objc func getAccessId( + @objc func startSession( projectId: String, projectURL: String, userId: String? = nil, hash: String? = nil, description: String? = nil - ) -> String? { - nonisolated(unsafe) var accessId: String? + ) -> StartSessionResult? { + nonisolated(unsafe) var session: StartSessionResult? let accessIdExpectation = XCTestExpectation(description: "wait for Access Id") platformAPI @@ -70,9 +70,9 @@ import MIRACLTrust userId: userId, hash: hash, description: description, - completionHandler: { code, error in - if let code = code { - accessId = code + completionHandler: { session1, error in + if let session1 { + session = session1 } else if let error = error { print("Error when creating access id: \(error)") } @@ -81,7 +81,7 @@ import MIRACLTrust ) _ = XCTWaiter.wait(for: [accessIdExpectation], timeout: operationTimeout) - return accessId + return session } @objc func startSigningSession( @@ -120,7 +120,41 @@ import MIRACLTrust nonisolated(unsafe) var verifiedSignature = false let expectation = XCTestExpectation(description: "Waiting for signature verification") - platformAPI.verifySignature(for: signingResult.signature, timestamp: signingResult.timestamp, clientId: clientId, clientSecret: clientSecret, projectId: projectId, projectURL: projectURL) { isVerified, _ in + platformAPI.verifySignature( + for: signingResult.signature, + timestamp: signingResult.timestamp, + clientId: clientId, + clientSecret: clientSecret, + projectId: projectId, + projectURL: projectURL + ) { isVerified, _ in + verifiedSignature = isVerified + expectation.fulfill() + } + _ = XCTWaiter.wait(for: [expectation], timeout: operationTimeout) + + return verifiedSignature + } + + @objc func verifySignature( + signature: Signature, + timestamp: Date, + clientId: String, + clientSecret: String, + projectId: String, + projectURL: String + ) -> Bool { + nonisolated(unsafe) var verifiedSignature = false + let expectation = XCTestExpectation(description: "Waiting for signature verification") + + platformAPI.verifySignature( + for: signature, + timestamp: timestamp, + clientId: clientId, + clientSecret: clientSecret, + projectId: projectId, + projectURL: projectURL + ) { isVerified, _ in verifiedSignature = isVerified expectation.fulfill() } @@ -164,23 +198,44 @@ import MIRACLTrust userId: String? = nil, hash: String? = nil, description: String? = nil - ) async throws -> String { - let accessId: String = try await withCheckedThrowingContinuation { continuation in + ) async throws -> StartSessionResult { + let session: StartSessionResult = try await withCheckedThrowingContinuation { continuation in platformAPI.getAccessId( projectURL: projectURL, projectId: projectId, userId: userId, hash: hash, description: description - ) { accessId, error in - if let accessId { - continuation.resume(returning: accessId) + ) { session, error in + if let session { + continuation.resume(returning: session) } else if let error { continuation.resume(throwing: error) } } } - return accessId + return session + } + + func getSessionStatus( + projectURL: String, + webOTT: String + ) async throws -> SessionStatusResponse { + let sessionStatusResponse: SessionStatusResponse = + try await withCheckedThrowingContinuation { continuation in + platformAPI.accessRequest( + projectURL: projectURL, + webOTT: webOTT + ) { response, error in + if let response { + continuation.resume(returning: response) + } else if let error { + continuation.resume(throwing: error) + } + } + } + + return sessionStatusResponse } } From 7cd3d873f38e40c71cbde4fbfa004f38ed7c2c0f Mon Sep 17 00:00:00 2001 From: Radoslav Penev Date: Mon, 20 Oct 2025 10:35:52 +0300 Subject: [PATCH 2/2] chore: bump version to 1.7.1 --- MIRACLTrust.podspec | 2 +- .../MIRACLTrust.xcodeproj/project.pbxproj | 20 +++++++++---------- README.md | 2 +- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/MIRACLTrust.podspec b/MIRACLTrust.podspec index 0547711..f36d73e 100644 --- a/MIRACLTrust.podspec +++ b/MIRACLTrust.podspec @@ -5,7 +5,7 @@ Pod::Spec.new do |s| s.name = "MIRACLTrust" s.summary = "MIRACL Trust SDK for iOS" s.requires_arc = true - s.version = "1.7.0" + s.version = "1.7.1" s.license = { :type => "Apache2", :file => "LICENSE" } s.author = { "MIRACL" => "operations@miracl.com" } s.homepage = "https://github.com/miracl/trust-sdk-ios" diff --git a/MIRACLTrust/MIRACLTrust.xcodeproj/project.pbxproj b/MIRACLTrust/MIRACLTrust.xcodeproj/project.pbxproj index c0ccfea..4107d75 100644 --- a/MIRACLTrust/MIRACLTrust.xcodeproj/project.pbxproj +++ b/MIRACLTrust/MIRACLTrust.xcodeproj/project.pbxproj @@ -1787,7 +1787,7 @@ GCC_WARN_UNUSED_VARIABLE = YES; IPHONEOS_DEPLOYMENT_TARGET = 13.2; MARKETING_VERSION = "$(MIRACL_SDK_VERSION)"; - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; MTL_FAST_MATH = YES; ONLY_ACTIVE_ARCH = YES; @@ -1852,7 +1852,7 @@ GCC_WARN_UNUSED_VARIABLE = YES; IPHONEOS_DEPLOYMENT_TARGET = 13.2; MARKETING_VERSION = "$(MIRACL_SDK_VERSION)"; - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; MTL_ENABLE_DEBUG_INFO = NO; MTL_FAST_MATH = YES; ONLY_ACTIVE_ARCH = YES; @@ -1878,7 +1878,7 @@ "@executable_path/Frameworks", "@loader_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; PRODUCT_BUNDLE_IDENTIFIER = "com.miracl.trust.sdk-ios.MIRACLTrustTests"; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_VERSION = 5.0; @@ -1898,7 +1898,7 @@ "@executable_path/Frameworks", "@loader_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; PRODUCT_BUNDLE_IDENTIFIER = "com.miracl.trust.sdk-ios.MIRACLTrustTests"; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_VERSION = 5.0; @@ -1920,7 +1920,7 @@ "@executable_path/Frameworks", "@loader_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.6.3; + MIRACL_SDK_VERSION = 1.7.1; PRODUCT_BUNDLE_IDENTIFIER = com.radoslavpenev.MIRACLTrustIntegrationTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OBJC_BRIDGING_HEADER = "MIRACLTrustIntegrationTests/Cases/MIRACLTrustIntegrationTests-Bridging-Header.h"; @@ -1945,7 +1945,7 @@ "@executable_path/Frameworks", "@loader_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.6.3; + MIRACL_SDK_VERSION = 1.7.1; PRODUCT_BUNDLE_IDENTIFIER = com.radoslavpenev.MIRACLTrustIntegrationTests; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_OBJC_BRIDGING_HEADER = "MIRACLTrustIntegrationTests/Cases/MIRACLTrustIntegrationTests-Bridging-Header.h"; @@ -1968,7 +1968,7 @@ "$(inherited)", "@executable_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; PRODUCT_BUNDLE_IDENTIFIER = "com.miracl.applclippoc.MIRACLTrust-Test-Host-App"; PRODUCT_NAME = "$(TARGET_NAME)"; SWIFT_APPROACHABLE_CONCURRENCY = YES; @@ -1990,7 +1990,7 @@ "$(inherited)", "@executable_path/Frameworks", ); - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; ONLY_ACTIVE_ARCH = NO; PRODUCT_BUNDLE_IDENTIFIER = "com.miracl.applclippoc.MIRACLTrust-Test-Host-App"; PRODUCT_NAME = "$(TARGET_NAME)"; @@ -2031,7 +2031,7 @@ "$(PROJECT_DIR)/MIRACLTrust-Sources/Crypto/src", ); MARKETING_VERSION = "$(MIRACL_SDK_VERSION)"; - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; MODULEMAP_FILE = "$(SRCROOT)/MIRACLTrust-Sources/MIRACLTrust.modulemap"; ONLY_ACTIVE_ARCH = YES; OTHER_CFLAGS = ( @@ -2080,7 +2080,7 @@ "$(PROJECT_DIR)/MIRACLTrust-Sources/Crypto/src", ); MARKETING_VERSION = "$(MIRACL_SDK_VERSION)"; - MIRACL_SDK_VERSION = 1.7.0; + MIRACL_SDK_VERSION = 1.7.1; MODULEMAP_FILE = "$(SRCROOT)/MIRACLTrust-Sources/MIRACLTrust.modulemap"; ONLY_ACTIVE_ARCH = NO; OTHER_CFLAGS = ( diff --git a/README.md b/README.md index b912089..abc73c5 100644 --- a/README.md +++ b/README.md @@ -29,7 +29,7 @@ To integrate using Apple's Swift package manager, without Xcode integration, add the following as a dependency to your Package.swift: ```bash -.package(url: "https://github.com/miracl/trust-sdk-ios", .upToNextMajor(from: "1.7.0")) +.package(url: "https://github.com/miracl/trust-sdk-ios", .upToNextMajor(from: "1.7.1")) ``` In both cases after the package is downloaded, go to the