From d4d37df00648e4663d175220485ae01001d64a4f Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 13:11:15 -0400 Subject: [PATCH 1/9] [Vertex AI] Use `URLSession(configuration: .ephemeral)` on iOS 18.4 sim --- .../Sources/GenAIURLSession.swift | 27 +++++++++++++++++++ .../Sources/GenerativeModel.swift | 2 +- .../Types/Public/Imagen/ImagenModel.swift | 2 +- 3 files changed, 29 insertions(+), 2 deletions(-) create mode 100644 FirebaseVertexAI/Sources/GenAIURLSession.swift diff --git a/FirebaseVertexAI/Sources/GenAIURLSession.swift b/FirebaseVertexAI/Sources/GenAIURLSession.swift new file mode 100644 index 00000000000..b99efd045e5 --- /dev/null +++ b/FirebaseVertexAI/Sources/GenAIURLSession.swift @@ -0,0 +1,27 @@ +// Copyright 2025 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 + +enum GenAIURLSession { + static let `default` = { + #if targetEnvironment(simulator) + if #available(iOS 18.4, *) { + return URLSession(configuration: .ephemeral) + } + #endif // targetEnvironment(simulator) + + return URLSession.shared + }() +} diff --git a/FirebaseVertexAI/Sources/GenerativeModel.swift b/FirebaseVertexAI/Sources/GenerativeModel.swift index 8ec905cc436..e21e6c826b2 100644 --- a/FirebaseVertexAI/Sources/GenerativeModel.swift +++ b/FirebaseVertexAI/Sources/GenerativeModel.swift @@ -74,7 +74,7 @@ public final class GenerativeModel: Sendable { toolConfig: ToolConfig? = nil, systemInstruction: ModelContent? = nil, requestOptions: RequestOptions, - urlSession: URLSession = .shared) { + urlSession: URLSession = GenAIURLSession.default) { self.modelResourceName = modelResourceName self.apiConfig = apiConfig generativeAIService = GenerativeAIService( diff --git a/FirebaseVertexAI/Sources/Types/Public/Imagen/ImagenModel.swift b/FirebaseVertexAI/Sources/Types/Public/Imagen/ImagenModel.swift index 90e5bb9f715..a829f616773 100644 --- a/FirebaseVertexAI/Sources/Types/Public/Imagen/ImagenModel.swift +++ b/FirebaseVertexAI/Sources/Types/Public/Imagen/ImagenModel.swift @@ -53,7 +53,7 @@ public final class ImagenModel { generationConfig: ImagenGenerationConfig?, safetySettings: ImagenSafetySettings?, requestOptions: RequestOptions, - urlSession: URLSession = .shared) { + urlSession: URLSession = GenAIURLSession.default) { self.modelResourceName = modelResourceName self.apiConfig = apiConfig generativeAIService = GenerativeAIService( From 568f6aea96669434ec6f9958cf0d41caf16dcd87 Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 19:19:39 -0400 Subject: [PATCH 2/9] Add visionOS config and docs --- FirebaseVertexAI/Sources/GenAIURLSession.swift | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/FirebaseVertexAI/Sources/GenAIURLSession.swift b/FirebaseVertexAI/Sources/GenAIURLSession.swift index b99efd045e5..39a45ca55d3 100644 --- a/FirebaseVertexAI/Sources/GenAIURLSession.swift +++ b/FirebaseVertexAI/Sources/GenAIURLSession.swift @@ -14,11 +14,22 @@ import Foundation +/// A namespace providing `URLSession` instances. enum GenAIURLSession { + /// The default `URLSession` instance for the SDK; returns `URLSession.shared` by default. + /// + /// - Important: On affected simulators (iOS 18.4+, visionOS 2.4+), this returns an ephemeral + /// `URLSession` instance as a workaround for a known system bug. static let `default` = { #if targetEnvironment(simulator) - if #available(iOS 18.4, *) { - return URLSession(configuration: .ephemeral) + // The iOS 18.4 and visionOS 2.4 simulators (included in Xcode 16.3) contain a bug in + // `URLSession` causing requests to fail. The following workaround, using an ephemeral session + // resolves the issue. See https://developer.apple.com/forums/thread/777999 for more details. + // + // Note: This bug only impacts the simulator, not real devices, and does not impact watchOS + // or tvOS. + if #available(iOS 18.4, tvOS 100.0, watchOS 100.0, visionOS 2.4, *) { + return URLSession(configuration: URLSessionConfiguration.ephemeral) } #endif // targetEnvironment(simulator) From b1600f9aebd216ed7ac74c6943ddc81f6503de51 Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 21:16:27 -0400 Subject: [PATCH 3/9] Add CHANGELOG entry --- FirebaseVertexAI/CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/FirebaseVertexAI/CHANGELOG.md b/FirebaseVertexAI/CHANGELOG.md index b33ebfd7192..77b0d2f6ebb 100644 --- a/FirebaseVertexAI/CHANGELOG.md +++ b/FirebaseVertexAI/CHANGELOG.md @@ -6,6 +6,8 @@ Note: This feature is in Public Preview and relies on experimental models, which means that it is not subject to any SLA or deprecation policy and could change in backwards-incompatible ways. +- [fixed] Fixed an issue where network requests would fail in the iOS 18.4 + simulator due to a `URLSession` bug introduced in Xcode 16.3. (#14696) # 11.11.0 - [added] Emits a warning when attempting to use an incompatible model with From f457d7cd06c8119bf18e8f18b2ce33b1034912ed Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 21:33:05 -0400 Subject: [PATCH 4/9] Try running on `Xcode_16.3` --- .github/workflows/vertexai.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/vertexai.yml b/.github/workflows/vertexai.yml index de39aecf7fa..3f4495e791f 100644 --- a/.github/workflows/vertexai.yml +++ b/.github/workflows/vertexai.yml @@ -99,6 +99,8 @@ jobs: include: - os: macos-15 xcode: Xcode_16.2 + - os: macos-15 + xcode: Xcode_16.3 runs-on: ${{ matrix.os }} needs: spm-package-resolved env: From ed30f77d15541028654601d0a161d880f2db3289 Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 21:34:43 -0400 Subject: [PATCH 5/9] Update CHANGELOG entry to refer to #14677 --- FirebaseVertexAI/CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/FirebaseVertexAI/CHANGELOG.md b/FirebaseVertexAI/CHANGELOG.md index 77b0d2f6ebb..3c3d1558bc4 100644 --- a/FirebaseVertexAI/CHANGELOG.md +++ b/FirebaseVertexAI/CHANGELOG.md @@ -7,7 +7,7 @@ which means that it is not subject to any SLA or deprecation policy and could change in backwards-incompatible ways. - [fixed] Fixed an issue where network requests would fail in the iOS 18.4 - simulator due to a `URLSession` bug introduced in Xcode 16.3. (#14696) + simulator due to a `URLSession` bug introduced in Xcode 16.3. (#14677) # 11.11.0 - [added] Emits a warning when attempting to use an incompatible model with From 353accd53d4a620c843c35a9ca25ed82e9105d0b Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Wed, 9 Apr 2025 21:49:08 -0400 Subject: [PATCH 6/9] Revert "Try running on `Xcode_16.3`" This reverts commit f457d7cd06c8119bf18e8f18b2ce33b1034912ed. --- .github/workflows/vertexai.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/vertexai.yml b/.github/workflows/vertexai.yml index 3f4495e791f..de39aecf7fa 100644 --- a/.github/workflows/vertexai.yml +++ b/.github/workflows/vertexai.yml @@ -99,8 +99,6 @@ jobs: include: - os: macos-15 xcode: Xcode_16.2 - - os: macos-15 - xcode: Xcode_16.3 runs-on: ${{ matrix.os }} needs: spm-package-resolved env: From 2a841b98a60bb19448adbd929d49238d0ea5250c Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Fri, 11 Apr 2025 16:02:26 -0400 Subject: [PATCH 7/9] Switch to Xcode 16.3 in CI --- .github/workflows/vertexai.yml | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/.github/workflows/vertexai.yml b/.github/workflows/vertexai.yml index de39aecf7fa..2b08ca897df 100644 --- a/.github/workflows/vertexai.yml +++ b/.github/workflows/vertexai.yml @@ -47,22 +47,22 @@ jobs: xcode: Xcode_16.2 target: iOS - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: iOS - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: tvOS - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: macOS - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: watchOS - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: catalyst - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 target: visionOS runs-on: ${{ matrix.os }} needs: spm-package-resolved @@ -98,7 +98,7 @@ jobs: os: [macos-15] include: - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 runs-on: ${{ matrix.os }} needs: spm-package-resolved env: @@ -137,11 +137,11 @@ jobs: swift_version: 5.9 warnings: - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 swift_version: 5.9 warnings: - os: macos-15 - xcode: Xcode_16.2 + xcode: Xcode_16.3 swift_version: 6.0 warnings: runs-on: ${{ matrix.os }} From 8945be6e27467bf0373bda017b9cf41f4711ac98 Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Fri, 11 Apr 2025 16:27:52 -0400 Subject: [PATCH 8/9] Replace `@_implementationOnly` with `internal` --- FirebaseVertexAI/Sources/VertexAI.swift | 2 +- FirebaseVertexAI/Sources/VertexLog.swift | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/FirebaseVertexAI/Sources/VertexAI.swift b/FirebaseVertexAI/Sources/VertexAI.swift index 112d117047d..c3ef7d2df73 100644 --- a/FirebaseVertexAI/Sources/VertexAI.swift +++ b/FirebaseVertexAI/Sources/VertexAI.swift @@ -18,7 +18,7 @@ import FirebaseCore import Foundation // Avoids exposing internal FirebaseCore APIs to Swift users. -@_implementationOnly import FirebaseCoreExtension +internal import FirebaseCoreExtension /// The Vertex AI for Firebase SDK provides access to Gemini models directly from your app. @available(iOS 15.0, macOS 12.0, macCatalyst 15.0, tvOS 15.0, watchOS 8.0, *) diff --git a/FirebaseVertexAI/Sources/VertexLog.swift b/FirebaseVertexAI/Sources/VertexLog.swift index ff94a2d435e..b98ed0f50f2 100644 --- a/FirebaseVertexAI/Sources/VertexLog.swift +++ b/FirebaseVertexAI/Sources/VertexLog.swift @@ -15,7 +15,7 @@ import Foundation import os.log -@_implementationOnly import FirebaseCoreExtension +internal import FirebaseCoreExtension enum VertexLog { /// Log message codes for the Vertex AI SDK From fb37945785fb438165b9a166d2351115fa09a6be Mon Sep 17 00:00:00 2001 From: Andrew Heard Date: Fri, 11 Apr 2025 16:42:14 -0400 Subject: [PATCH 9/9] Fix imports --- FirebaseVertexAI/Tests/Unit/GenerativeModelTests.swift | 5 ++--- FirebaseVertexAI/Tests/Unit/VertexComponentTests.swift | 3 +-- 2 files changed, 3 insertions(+), 5 deletions(-) diff --git a/FirebaseVertexAI/Tests/Unit/GenerativeModelTests.swift b/FirebaseVertexAI/Tests/Unit/GenerativeModelTests.swift index 290238445c5..8dd2cf07e42 100644 --- a/FirebaseVertexAI/Tests/Unit/GenerativeModelTests.swift +++ b/FirebaseVertexAI/Tests/Unit/GenerativeModelTests.swift @@ -17,7 +17,7 @@ import FirebaseAuthInterop import FirebaseCore import XCTest -@testable import FirebaseVertexAI +@testable public import FirebaseVertexAI @available(iOS 15.0, macOS 12.0, macCatalyst 15.0, tvOS 15.0, watchOS 8.0, *) final class GenerativeModelTests: XCTestCase { @@ -1690,8 +1690,7 @@ struct AppCheckErrorFake: Error {} @available(iOS 15.0, macOS 12.0, macCatalyst 15.0, tvOS 15.0, watchOS 8.0, *) extension SafetyRating: Swift.Comparable { - public static func < (lhs: FirebaseVertexAI.SafetyRating, - rhs: FirebaseVertexAI.SafetyRating) -> Bool { + public static func < (lhs: SafetyRating, rhs: SafetyRating) -> Bool { return lhs.category.rawValue < rhs.category.rawValue } } diff --git a/FirebaseVertexAI/Tests/Unit/VertexComponentTests.swift b/FirebaseVertexAI/Tests/Unit/VertexComponentTests.swift index 6535ba26137..3f9f6622ead 100644 --- a/FirebaseVertexAI/Tests/Unit/VertexComponentTests.swift +++ b/FirebaseVertexAI/Tests/Unit/VertexComponentTests.swift @@ -13,11 +13,10 @@ // limitations under the License. @preconcurrency import FirebaseCore +internal import FirebaseCoreExtension import Foundation import XCTest -@_implementationOnly import FirebaseCoreExtension - @testable import FirebaseVertexAI @available(iOS 15.0, macOS 12.0, macCatalyst 15.0, tvOS 15.0, watchOS 8.0, *)