diff --git a/.github/actions/uitests/action.yml b/.github/actions/uitests/action.yml index 2b939368f..4bec323b8 100644 --- a/.github/actions/uitests/action.yml +++ b/.github/actions/uitests/action.yml @@ -150,6 +150,16 @@ runs: Example.xcodeproj/xcshareddata/xcschemes/SUI_UITests.xcscheme \ Example.xcodeproj/xcshareddata/xcschemes/OSUI_UITests.xcscheme + - name: Prepare isolated build directory + id: build-directory + shell: bash + run: | + build_root="${RUNNER_TEMP:-/tmp}/uitests-build-${GITHUB_RUN_ID}-${GITHUB_RUN_ATTEMPT:-0}-${{ inputs.artifact-name }}" + derived_data_path="$build_root/DerivedData" + rm -rf "$derived_data_path" + mkdir -p "$derived_data_path" + echo "derived-data-path=$derived_data_path" >> "$GITHUB_OUTPUT" + - name: Record baseline images with SwiftUI id: record-baseline if: steps.reference.outputs.needs-record == 'true' @@ -219,6 +229,7 @@ runs: -destination "${{ inputs.destination }}" \ -skipMacroValidation \ -skipPackagePluginValidation \ + -derivedDataPath "${{ steps.build-directory.outputs.derived-data-path }}" \ 2>&1 || record_status=$? if [[ "$record_status" -ne 0 ]]; then @@ -254,7 +265,7 @@ runs: shell: bash run: | cd Example - uitest_tmp="${RUNNER_TEMP:-/tmp}/uitests-${GITHUB_RUN_ID}-${{ inputs.platform }}" + uitest_tmp="${RUNNER_TEMP:-/tmp}/uitests-${GITHUB_RUN_ID}-${GITHUB_RUN_ATTEMPT:-0}-${{ inputs.artifact-name }}" rm -rf "$uitest_tmp" mkdir -p "$uitest_tmp/artifacts" result_bundle="$uitest_tmp/${{ inputs.platform }}-uitest.xcresult" @@ -271,6 +282,7 @@ runs: -destination "${{ inputs.destination }}" \ -skipMacroValidation \ -skipPackagePluginValidation \ + -derivedDataPath "${{ steps.build-directory.outputs.derived-data-path }}" \ -resultBundlePath "$result_bundle" \ 2>&1 | tee "$test_log" @@ -311,3 +323,12 @@ runs: path: ${{ steps.uitest.outputs.xcresult_archive }} archive: false retention-days: 7 + + - name: Clean up isolated build directory + if: always() + shell: bash + run: | + derived_data_path="${{ steps.build-directory.outputs.derived-data-path }}" + if [[ -n "$derived_data_path" ]]; then + rm -rf "$derived_data_path" + fi diff --git a/.github/workflows/compatibility_tests.yml b/.github/workflows/compatibility_tests.yml index 89a4f4604..fbcca6bf6 100644 --- a/.github/workflows/compatibility_tests.yml +++ b/.github/workflows/compatibility_tests.yml @@ -98,6 +98,15 @@ jobs: shell: bash - name: Install xcbeautify run: brew install xcbeautify + - name: Prepare isolated DerivedData + shell: bash + run: | + openswiftui_derived_data_path="${RUNNER_TEMP:-/tmp}/compatibility-ios-derived-data-${GITHUB_RUN_ID}-${GITHUB_RUN_ATTEMPT:-0}-${{ matrix.ios-version }}-${{ matrix.release }}-openswiftui" + swiftui_derived_data_path="${RUNNER_TEMP:-/tmp}/compatibility-ios-derived-data-${GITHUB_RUN_ID}-${GITHUB_RUN_ATTEMPT:-0}-${{ matrix.ios-version }}-${{ matrix.release }}-swiftui" + rm -rf "$openswiftui_derived_data_path" "$swiftui_derived_data_path" + mkdir -p "$openswiftui_derived_data_path" "$swiftui_derived_data_path" + echo "OPENSWIFTUI_DERIVED_DATA_PATH=$openswiftui_derived_data_path" >> "$GITHUB_ENV" + echo "SWIFTUI_DERIVED_DATA_PATH=$swiftui_derived_data_path" >> "$GITHUB_ENV" - name: Run compatibility tests on OpenSwiftUI + iOS run: | set -o pipefail @@ -110,6 +119,7 @@ jobs: -configuration Debug \ -destination "platform=iOS Simulator,OS=${{ matrix.ios-version }},name=${{ matrix.ios-simulator-name }},arch=x86_64" \ -only-testing:OpenSwiftUICompatibilityTests \ + -derivedDataPath "$OPENSWIFTUI_DERIVED_DATA_PATH" \ -skipMacroValidation \ -skipPackagePluginValidation \ ONLY_ACTIVE_ARCH=YES \ @@ -127,9 +137,20 @@ jobs: -configuration Debug \ -destination "platform=iOS Simulator,OS=${{ matrix.ios-version }},name=${{ matrix.ios-simulator-name }},arch=x86_64" \ -only-testing:OpenSwiftUICompatibilityTests \ + -derivedDataPath "$SWIFTUI_DERIVED_DATA_PATH" \ -skipMacroValidation \ -skipPackagePluginValidation \ ONLY_ACTIVE_ARCH=YES \ 2>&1 | xcbeautify --renderer github-actions --preserve-unbeautified env: OPENSWIFTUI_COMPATIBILITY_TEST: 1 + - name: Clean up isolated DerivedData + if: always() + shell: bash + run: | + if [[ -n "${OPENSWIFTUI_DERIVED_DATA_PATH:-}" ]]; then + rm -rf "$OPENSWIFTUI_DERIVED_DATA_PATH" + fi + if [[ -n "${SWIFTUI_DERIVED_DATA_PATH:-}" ]]; then + rm -rf "$SWIFTUI_DERIVED_DATA_PATH" + fi diff --git a/.github/workflows/ios.yml b/.github/workflows/ios.yml index 08cc737f1..f0d0b7501 100644 --- a/.github/workflows/ios.yml +++ b/.github/workflows/ios.yml @@ -45,6 +45,13 @@ jobs: shell: bash - name: Install xcbeautify run: brew install xcbeautify + - name: Prepare isolated DerivedData + shell: bash + run: | + derived_data_path="${RUNNER_TEMP:-/tmp}/ios-derived-data-${GITHUB_RUN_ID}-${GITHUB_RUN_ATTEMPT:-0}-${{ matrix.ios-version }}-${{ matrix.release }}" + rm -rf "$derived_data_path" + mkdir -p "$derived_data_path" + echo "DERIVED_DATA_PATH=$derived_data_path" >> "$GITHUB_ENV" - name: Build test target in debug mode run: | set -o pipefail @@ -55,6 +62,7 @@ jobs: -scheme OpenSwiftUI \ -configuration Debug \ -destination "platform=iOS Simulator,OS=${{ matrix.ios-version }},name=${{ matrix.ios-simulator-name }},arch=x86_64" \ + -derivedDataPath "$DERIVED_DATA_PATH" \ -skipMacroValidation \ -skipPackagePluginValidation \ ONLY_ACTIVE_ARCH=YES \ @@ -68,7 +76,15 @@ jobs: -scheme OpenSwiftUI \ -configuration Debug \ -destination "platform=iOS Simulator,OS=${{ matrix.ios-version }},name=${{ matrix.ios-simulator-name }},arch=x86_64" \ + -derivedDataPath "$DERIVED_DATA_PATH" \ -skipMacroValidation \ -skipPackagePluginValidation \ ONLY_ACTIVE_ARCH=YES \ 2>&1 | xcbeautify --renderer github-actions --preserve-unbeautified + - name: Clean up isolated DerivedData + if: always() + shell: bash + run: | + if [[ -n "${DERIVED_DATA_PATH:-}" ]]; then + rm -rf "$DERIVED_DATA_PATH" + fi diff --git a/Example/Example_Legacy.xcodeproj/project.pbxproj b/Example/Example_Legacy.xcodeproj/project.pbxproj index 55732e662..a4aba69a9 100644 --- a/Example/Example_Legacy.xcodeproj/project.pbxproj +++ b/Example/Example_Legacy.xcodeproj/project.pbxproj @@ -1375,10 +1375,10 @@ /* Begin XCRemoteSwiftPackageReference section */ 275752022DEE147E003E467C /* XCRemoteSwiftPackageReference "swift-snapshot-testing" */ = { isa = XCRemoteSwiftPackageReference; - repositoryURL = "https://github.com/OpenSwiftUIProject/swift-snapshot-testing"; + repositoryURL = "https://github.com/OpenSwiftUIProject/swift-snapshot-testing.git"; requirement = { kind = exactVersion; - version = "1.18.9-osui"; + version = "1.19.2"; }; }; 278EF52B2E2272F2009C32EB /* XCRemoteSwiftPackageReference "equatable" */ = { diff --git a/Example/OpenSwiftUIUITests/Export.swift b/Example/OpenSwiftUIUITests/Export.swift index d8b1f9fea..0b708e066 100644 --- a/Example/OpenSwiftUIUITests/Export.swift +++ b/Example/OpenSwiftUIUITests/Export.swift @@ -7,10 +7,10 @@ import SnapshotTesting #if OPENSWIFTUI @_exported import OpenSwiftUI -let shouldRecord: Bool? = nil +let shouldRecord: SnapshotTestingConfiguration.Record? = nil #else @_exported import SwiftUI -let shouldRecord: Bool? = true +let shouldRecord: SnapshotTestingConfiguration.Record? = .all public struct ViewRendererVendor: RawRepresentable, Hashable, CaseIterable { public let rawValue: String diff --git a/Example/OpenSwiftUIUITests/UITests/SnapshotTesting+Testing.swift b/Example/OpenSwiftUIUITests/UITests/SnapshotTesting+Testing.swift index d1b9c0d5d..ad6c112e1 100644 --- a/Example/OpenSwiftUIUITests/UITests/SnapshotTesting+Testing.swift +++ b/Example/OpenSwiftUIUITests/UITests/SnapshotTesting+Testing.swift @@ -67,7 +67,7 @@ func openSwiftUIAssertSnapshot( perceptualPrecision: Float = 1, size: CGSize = defaultSize, named name: String? = nil, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, @@ -93,7 +93,7 @@ func openSwiftUIAssertSnapshot( of value: @autoclosure () -> V, as snapshotting: Snapshotting, named name: String? = nil, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, @@ -119,7 +119,7 @@ func openSwiftUIAssertSnapshot( of value: @autoclosure () -> V, as snapshotting: Snapshotting, named name: String? = nil, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, @@ -146,7 +146,7 @@ func openSwiftUIControllerAssertSnapshot( of value: @autoclosure () -> V, as snapshotting: Snapshotting, named name: String? = nil, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, @@ -173,7 +173,7 @@ private func openSwiftUIAssertSnapshot( of value: @autoclosure () -> Value, as snapshotting: Snapshotting, named name: String? = nil, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, @@ -214,7 +214,7 @@ func openSwiftUIAssertAnimationSnapshot( precision: Float = 1, perceptualPrecision: Float = 1, size: CGSize = defaultSize, - record recording: Bool? = shouldRecord, + record recording: SnapshotTestingConfiguration.Record? = shouldRecord, timeout: TimeInterval = 5, fileID: StaticString = #fileID, file filePath: StaticString = #filePath, diff --git a/Example/Tuist/Package.resolved b/Example/Tuist/Package.resolved index 4eb1369c6..f3411de98 100644 --- a/Example/Tuist/Package.resolved +++ b/Example/Tuist/Package.resolved @@ -1,5 +1,5 @@ { - "originHash" : "0f8a072585da3899cfbf7b80693774376f747e63c0805d25e6f792f78ccbdfd1", + "originHash" : "41017ad3153c643b413e18cfea9f01329068bcfa5b7c9d3847007c4d59856986", "pins" : [ { "identity" : "equatable", @@ -76,10 +76,10 @@ { "identity" : "swift-snapshot-testing", "kind" : "remoteSourceControl", - "location" : "https://github.com/OpenSwiftUIProject/swift-snapshot-testing", + "location" : "https://github.com/OpenSwiftUIProject/swift-snapshot-testing.git", "state" : { - "revision" : "6456a4fd141fa6ae4aedfb433987038293220cfd", - "version" : "1.18.9-osui" + "revision" : "ad5e3190cc63dc288f28546f9c6827efc1e9d495", + "version" : "1.19.2" } }, { diff --git a/Example/Tuist/Package.swift b/Example/Tuist/Package.swift index 4f647a823..836496d33 100644 --- a/Example/Tuist/Package.swift +++ b/Example/Tuist/Package.swift @@ -32,7 +32,7 @@ var dependencies: [PackageDescription.Package.Dependency] = [ .package(url: "https://github.com/swiftlang/swift-syntax.git", from: "601.0.0"), .package(url: "https://github.com/OpenSwiftUIProject/equatable.git", branch: "main"), .package(url: "https://github.com/OpenSwiftUIProject/SymbolLocator.git", from: "0.2.0"), - .package(url: "https://github.com/OpenSwiftUIProject/swift-snapshot-testing", exact: "1.18.9-osui"), + .package(url: "https://github.com/OpenSwiftUIProject/swift-snapshot-testing.git", exact: "1.19.2"), ] if enableLookInsideServer { diff --git a/Sources/OpenSwiftUI/App/App/App.swift b/Sources/OpenSwiftUI/App/App/App.swift index f740ee1d7..d550a792a 100644 --- a/Sources/OpenSwiftUI/App/App/App.swift +++ b/Sources/OpenSwiftUI/App/App/App.swift @@ -129,12 +129,14 @@ public protocol App { init() /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER /// The global default renderer configuration used by the app lifecycle. /// /// If set, OpenSwiftUI applies this configuration to renderers that it /// creates for the app. @_spi(StdoutRenderer) nonisolated static var rendererConfiguration: _RendererConfiguration? { get } + #endif /* OpenSwiftUI Addition End */ } @@ -151,10 +153,12 @@ extension App { public static func main() { let app = Self() /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER if let rendererConfiguration = Self.rendererConfiguration, case let .stdout(options) = rendererConfiguration.renderer { runStdoutApp(app, options: options) } + #endif /* OpenSwiftUI Addition End */ runApp(app) } diff --git a/Sources/OpenSwiftUI/App/App/Stdout/StdoutApp.swift b/Sources/OpenSwiftUI/App/App/Stdout/StdoutApp.swift index 549903b52..f36ae1c10 100644 --- a/Sources/OpenSwiftUI/App/App/Stdout/StdoutApp.swift +++ b/Sources/OpenSwiftUI/App/App/Stdout/StdoutApp.swift @@ -2,6 +2,7 @@ // StdoutApp.swift // OpenSwiftUI +#if !OPENSWIFTUI_SWIFTUI_RENDERER #if canImport(Darwin) import Darwin #elseif canImport(Glibc) @@ -45,3 +46,4 @@ func runStdoutApp( } exit(0) } +#endif diff --git a/Sources/OpenSwiftUICore/Render/DisplayList/DisplayListViewRenderer.swift b/Sources/OpenSwiftUICore/Render/DisplayList/DisplayListViewRenderer.swift index 6299e83a7..95a641175 100644 --- a/Sources/OpenSwiftUICore/Render/DisplayList/DisplayListViewRenderer.swift +++ b/Sources/OpenSwiftUICore/Render/DisplayList/DisplayListViewRenderer.swift @@ -75,7 +75,9 @@ extension DisplayList { case updating case rasterizing /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER case stdout + #endif /* OpenSwiftUI Addition End */ } @@ -98,7 +100,9 @@ extension DisplayList { case .default: state == .updating case .rasterized: state == .rasterizing /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER case .stdout: state == .stdout + #endif /* OpenSwiftUI Addition End */ } if !isValid { @@ -117,10 +121,12 @@ extension DisplayList { rasterizer.renderer.platformViewMode = options.drawsPlatformViews ? .rendered(update: true) : .unsupported rasterizer.host = host /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER case let .stdout(options): let stdoutRenderer = renderer as! StdoutDisplayListRenderer stdoutRenderer.options = options stdoutRenderer.host = host + #endif /* OpenSwiftUI Addition End */ } } else { @@ -139,6 +145,7 @@ extension DisplayList { renderer = rasterizer state = .rasterizing /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER case let .stdout(options): renderer = StdoutDisplayListRenderer( platform: platform, @@ -146,6 +153,7 @@ extension DisplayList { options: options ) state = .stdout + #endif /* OpenSwiftUI Addition End */ } } diff --git a/Sources/OpenSwiftUICore/Render/DisplayList/StdoutRendererHost.swift b/Sources/OpenSwiftUICore/Render/DisplayList/StdoutRendererHost.swift index be8641e22..4469c68cd 100644 --- a/Sources/OpenSwiftUICore/Render/DisplayList/StdoutRendererHost.swift +++ b/Sources/OpenSwiftUICore/Render/DisplayList/StdoutRendererHost.swift @@ -2,6 +2,7 @@ // StdoutRendererHost.swift // OpenSwiftUICore +#if !OPENSWIFTUI_SWIFTUI_RENDERER import Foundation // MARK: - StdoutRendererHost @@ -103,3 +104,4 @@ final package class StdoutRendererHost: ViewRendererHost, ViewGraphRend } private final class StdoutPlatformViewDefinition: PlatformViewDefinition, @unchecked Sendable {} +#endif diff --git a/Sources/OpenSwiftUICore/Render/RendererConfiguration.swift b/Sources/OpenSwiftUICore/Render/RendererConfiguration.swift index 4677d3a4e..86bc75764 100644 --- a/Sources/OpenSwiftUICore/Render/RendererConfiguration.swift +++ b/Sources/OpenSwiftUICore/Render/RendererConfiguration.swift @@ -23,10 +23,12 @@ public struct _RendererConfiguration { indirect case rasterized(_ options: _RendererConfiguration.RasterizationOptions = .init()) /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER /// A renderer that writes a textual representation of the display list /// to standard output. @_spi(StdoutRenderer) indirect case stdout(_ options: _RendererConfiguration.StdoutOptions = .init()) + #endif /* OpenSwiftUI Addition End */ } @@ -51,11 +53,13 @@ public struct _RendererConfiguration { /* OpenSwiftUI Addition Begin */ + #if !OPENSWIFTUI_SWIFTUI_RENDERER /// Returns a configuration to render the display list to standard output. @_spi(StdoutRenderer) public static func stdout(_ options: _RendererConfiguration.StdoutOptions = .init()) -> _RendererConfiguration { _RendererConfiguration(renderer: .stdout(options)) } + #endif /* OpenSwiftUI Addition End */