From 9b3ca1ab4a26c2ea300a6d51fd95f38f826d80bc Mon Sep 17 00:00:00 2001 From: Srushti Vaidya Date: Sun, 15 Jun 2025 02:33:35 +0530 Subject: [PATCH 1/2] Add tests for ExchangeTokenRequest --- ExchangeTokenRequestTests.swift | 151 ++++++++++++++++++++++++++++++++ 1 file changed, 151 insertions(+) create mode 100644 ExchangeTokenRequestTests.swift diff --git a/ExchangeTokenRequestTests.swift b/ExchangeTokenRequestTests.swift new file mode 100644 index 00000000000..832ec623304 --- /dev/null +++ b/ExchangeTokenRequestTests.swift @@ -0,0 +1,151 @@ +// Copyright 2023 Google LLC +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +import Foundation +import XCTest + +@testable import FirebaseAuth +import FirebaseCore + +/// @class ExchangeTokenRequestTests +/// @brief Tests for the @c ExchangeTokenRequest struct. +@available(iOS 13, *) +class ExchangeTokenRequestTests: XCTestCase { + // MARK: - Constants for Testing + + let kAPIKey = "test-api-key" + let kProjectID = "test-project-id" + let kLocation = "us-east1" + let kTenantID = "test-tenant-id-123" + let kIdToken = "a-very-long-and-secure-oidc-token-string" + let kIdpConfigId = "oidc.my-test-provider" + + let kProductionHost = "identityplatform.googleapis.com" + let kStagingHost = "staging-identityplatform.sandbox.googleapis.com" + + // MARK: - Test Cases + + func testProductionURLIsCorrectlyConstructed() { + let (auth, app) = createTestAuthInstance( + projectID: kProjectID, + location: kLocation, + tenantId: kTenantID + ) + _ = app + + let request = ExchangeTokenRequest( + idToken: kIdToken, + idpConfigID: kIdpConfigId, + config: auth.requestConfiguration, + useStaging: false + ) + + let expectedHost = "\(kLocation)-\(kProductionHost)" + let expectedURL = "https://\(expectedHost)/v2beta/projects/\(kProjectID)" + + "/locations/\(kLocation)/tenants/\(kTenantID)/idpConfigs/\(kIdpConfigId):exchangeOidcToken?key=\(kAPIKey)" + + XCTAssertEqual(request.requestURL().absoluteString, expectedURL) + } + + func testProductionURLIsCorrectlyConstructedForGlobalLocation() { + let (auth, app) = createTestAuthInstance( + projectID: kProjectID, + location: "prod-global", + tenantId: kTenantID + ) + _ = app + + let request = ExchangeTokenRequest( + idToken: kIdToken, + idpConfigID: kIdpConfigId, + config: auth.requestConfiguration, + useStaging: false + ) + + let expectedHost = kProductionHost + let expectedURL = "https://\(expectedHost)/v2beta/projects/\(kProjectID)" + + "/locations/global/tenants/\(kTenantID)/idpConfigs/\(kIdpConfigId):exchangeOidcToken?key=\(kAPIKey)" + + XCTAssertEqual(request.requestURL().absoluteString, expectedURL) + } + + func testStagingURLIsCorrectlyConstructed() { + let (auth, app) = createTestAuthInstance( + projectID: kProjectID, + location: kLocation, + tenantId: kTenantID + ) + _ = app + + let request = ExchangeTokenRequest( + idToken: kIdToken, + idpConfigID: kIdpConfigId, + config: auth.requestConfiguration, + useStaging: true + ) + + let expectedHost = "\(kLocation)-\(kStagingHost)" + let expectedURL = "https://\(expectedHost)/v2beta/projects/\(kProjectID)" + + "/locations/\(kLocation)/tenants/\(kTenantID)/idpConfigs/\(kIdpConfigId):exchangeOidcToken?key=\(kAPIKey)" + + XCTAssertEqual(request.requestURL().absoluteString, expectedURL) + } + + func testUnencodedHTTPBodyIsCorrect() { + let (auth, app) = createTestAuthInstance( + projectID: kProjectID, + location: kLocation, + tenantId: kTenantID + ) + _ = app + + let request = ExchangeTokenRequest( + idToken: kIdToken, + idpConfigID: kIdpConfigId, + config: auth.requestConfiguration + ) + + let body = request.unencodedHTTPRequestBody + XCTAssertNotNil(body) + XCTAssertEqual(body?.count, 1) + XCTAssertEqual(body?["id_token"] as? String, kIdToken) + } + + // MARK: - Helper Function + + private func createTestAuthInstance(projectID: String?, location: String?, + tenantId: String?) -> (auth: Auth, app: FirebaseApp) { + let appName = "TestApp-\(UUID().uuidString)" + let options = FirebaseOptions( + googleAppID: "1:1234567890:ios:abcdef123456", + gcmSenderID: "1234567890" + ) + options.apiKey = kAPIKey + if let projectID = projectID { + options.projectID = projectID + } + + if FirebaseApp.app(name: appName) != nil { + FirebaseApp.app(name: appName)?.delete { _ in } + } + let app = FirebaseApp(instanceWithName: appName, options: options) + + let auth = Auth(app: app) + auth.app = app + auth.requestConfiguration.location = location + auth.requestConfiguration.tenantId = tenantId + + return (auth, app) + } +} From 0a8642a71363b11e12425a51417b5487b1e17c3a Mon Sep 17 00:00:00 2001 From: Srushti Vaidya Date: Sun, 15 Jun 2025 02:40:58 +0530 Subject: [PATCH 2/2] update comments in exchange token tests --- ExchangeTokenRequestTests.swift | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/ExchangeTokenRequestTests.swift b/ExchangeTokenRequestTests.swift index 832ec623304..c746e997d1f 100644 --- a/ExchangeTokenRequestTests.swift +++ b/ExchangeTokenRequestTests.swift @@ -18,8 +18,7 @@ import XCTest @testable import FirebaseAuth import FirebaseCore -/// @class ExchangeTokenRequestTests -/// @brief Tests for the @c ExchangeTokenRequest struct. +/// Tests for `ExchangeTokenRequest` @available(iOS 13, *) class ExchangeTokenRequestTests: XCTestCase { // MARK: - Constants for Testing @@ -36,6 +35,7 @@ class ExchangeTokenRequestTests: XCTestCase { // MARK: - Test Cases + /// Tests that the production URL is correctly formed for a specific region. func testProductionURLIsCorrectlyConstructed() { let (auth, app) = createTestAuthInstance( projectID: kProjectID, @@ -58,6 +58,7 @@ class ExchangeTokenRequestTests: XCTestCase { XCTAssertEqual(request.requestURL().absoluteString, expectedURL) } + /// Tests that the production URL is correctly formed for the "prod-global" location. func testProductionURLIsCorrectlyConstructedForGlobalLocation() { let (auth, app) = createTestAuthInstance( projectID: kProjectID, @@ -80,6 +81,7 @@ class ExchangeTokenRequestTests: XCTestCase { XCTAssertEqual(request.requestURL().absoluteString, expectedURL) } + /// Tests that the staging URL is correctly formed. func testStagingURLIsCorrectlyConstructed() { let (auth, app) = createTestAuthInstance( projectID: kProjectID, @@ -102,6 +104,7 @@ class ExchangeTokenRequestTests: XCTestCase { XCTAssertEqual(request.requestURL().absoluteString, expectedURL) } + /// Tests that the unencoded HTTP body contains the correct id_token. func testUnencodedHTTPBodyIsCorrect() { let (auth, app) = createTestAuthInstance( projectID: kProjectID, @@ -124,6 +127,7 @@ class ExchangeTokenRequestTests: XCTestCase { // MARK: - Helper Function + /// Creates a test FirebaseApp and Auth instance with specified configurations. private func createTestAuthInstance(projectID: String?, location: String?, tenantId: String?) -> (auth: Auth, app: FirebaseApp) { let appName = "TestApp-\(UUID().uuidString)"