Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Swift Language Support: Drop <5.9, Add 6.0 #26

Merged
merged 4 commits into from
Jun 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 24 additions & 24 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,45 +16,45 @@ concurrency:
jobs:
library:
name: macOS
runs-on: macos-14
strategy:
matrix:
xcode: ['14.3.1']
xcode: ['15.4']
config: ['debug', 'release']
runs-on: macos-13
steps:
- uses: actions/checkout@v3
- uses: actions/checkout@v4
- name: Select Xcode ${{ matrix.xcode }}
run: sudo xcode-select -s /Applications/Xcode_${{ matrix.xcode }}.app
- name: Run ${{ matrix.config }} tests
run: CONFIG=${{ matrix.config }} make test

linux:
name: Linux
name: Linux (Swift ${{ matrix.swift }})
runs-on: ubuntu-latest
strategy:
matrix:
os: [ubuntu-20.04]
config: ['debug', 'release']
runs-on: ${{ matrix.os }}
swift:
- '5.10'
container: swift:${{ matrix.swift }}
steps:
- uses: actions/checkout@v3
- name: Build
run: swift build
- uses: actions/checkout@v4
- name: Run tests
run: swift test -c ${{ matrix.config }}

wasm:
name: Wasm
runs-on: ubuntu-latest
strategy:
matrix:
include:
- { toolchain: wasm-5.7.1-RELEASE }
steps:
- uses: actions/checkout@v3
- run: echo "${{ matrix.toolchain }}" > .swift-version
- uses: swiftwasm/[email protected]
with:
shell-action: carton test --environment node
name: Wasm
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: bytecodealliance/actions/wasmtime/setup@v1
- uses: swiftwasm/setup-swiftwasm@v1
with:
swift-version: "wasm-5.9.2-RELEASE"
- name: Build tests
run: swift build --triple wasm32-unknown-wasi --build-tests
- name: Run tests
run: wasmtime --dir . .build/debug/swift-concurrency-extrasPackageTests.wasm

windows:
name: Windows
Expand All @@ -66,9 +66,9 @@ jobs:
steps:
- uses: compnerd/gha-setup-swift@main
with:
branch: swift-5.8-release
tag: 5.8-RELEASE
branch: swift-5.10-release
tag: 5.10-RELEASE

- uses: actions/checkout@v3
- uses: actions/checkout@v4
- name: Run tests
run: swift build -c ${{ matrix.config }}
19 changes: 7 additions & 12 deletions Package.swift
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// swift-tools-version: 5.6
// swift-tools-version: 5.9

import PackageDescription

Expand Down Expand Up @@ -36,14 +36,9 @@ let package = Package(
)
#endif

//for target in package.targets {
// target.swiftSettings = target.swiftSettings ?? []
// target.swiftSettings?.append(
// .unsafeFlags([
// "-c", "release",
// "-emit-module-interface", "-enable-library-evolution",
// "-Xfrontend", "-warn-concurrency",
// "-Xfrontend", "-enable-actor-data-race-checks",
// ])
// )
//}
for target in package.targets {
target.swiftSettings = target.swiftSettings ?? []
target.swiftSettings!.append(contentsOf: [
.enableExperimentalFeature("StrictConcurrency")
])
}
37 changes: 37 additions & 0 deletions [email protected]
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
// swift-tools-version: 6.0

import PackageDescription

let package = Package(
name: "swift-concurrency-extras",
platforms: [
.iOS(.v13),
.macOS(.v10_15),
.tvOS(.v13),
.watchOS(.v6),
],
products: [
.library(
name: "ConcurrencyExtras",
targets: ["ConcurrencyExtras"]
)
],
targets: [
.target(
name: "ConcurrencyExtras"
),
.testTarget(
name: "ConcurrencyExtrasTests",
dependencies: [
"ConcurrencyExtras"
]
),
]
)

#if !os(Windows)
// Add the documentation compiler plugin if possible
package.dependencies.append(
.package(url: "https://github.com/apple/swift-docc-plugin", from: "1.0.0")
)
#endif
60 changes: 0 additions & 60 deletions Sources/ConcurrencyExtras/AsyncStream.swift
Original file line number Diff line number Diff line change
Expand Up @@ -65,66 +65,6 @@ extension AsyncStream {
}
}

#if swift(<5.9)
/// Constructs and returns a stream along with its backing continuation.
///
/// A back-port of [SE-0388: Convenience Async[Throwing]Stream.makeStream methods][se-0388].
///
/// This is handy for immediately escaping the continuation from an async stream, which
/// typically requires multiple steps:
///
/// ```swift
/// var _continuation: AsyncStream<Int>.Continuation!
/// let stream = AsyncStream<Int> { continuation = $0 }
/// let continuation = _continuation!
///
/// // vs.
///
/// let (stream, continuation) = AsyncStream.makeStream(of: Int.self)
/// ```
///
/// This tool is usually used for tests where we need to supply an async sequence to a
/// dependency endpoint and get access to its continuation so that we can emulate the dependency
/// emitting data. For example, suppose you have a dependency exposing an async sequence for
/// listening to notifications. To test this you can use `makeStream`:
///
/// ```swift
/// func testScreenshots() {
/// let screenshots = AsyncStream.makeStream(of: Void.self)
///
/// let model = withDependencies {
/// $0.screenshots = { screenshots.stream }
/// } operation: {
/// FeatureModel()
/// }
///
/// XCTAssertEqual(model.screenshotCount, 0)
/// screenshots.continuation.yield() // Simulate a screenshot being taken.
/// XCTAssertEqual(model.screenshotCount, 1)
/// }
/// ```
///
/// > Warning: ⚠️ `AsyncStream` does not support multiple subscribers, therefore you can only
/// > use this helper to test features that do not subscribe multiple times to the dependency
/// > endpoint.
///
/// [se-0388]: https://github.com/apple/swift-evolution/blob/main/proposals/0388-async-stream-factory.md
///
/// - Parameters:
/// - elementType: The type of element the `AsyncStream` produces.
/// - limit: A Continuation.BufferingPolicy value to set the stream’s buffering behavior. By
/// default, the stream buffers an unlimited number of elements. You can also set the policy
/// to buffer a specified number of oldest or newest elements.
/// - Returns: An `AsyncStream`.
public static func makeStream(
of elementType: Element.Type = Element.self,
bufferingPolicy limit: Continuation.BufferingPolicy = .unbounded
) -> (stream: Self, continuation: Continuation) {
var continuation: Continuation!
return (Self(elementType, bufferingPolicy: limit) { continuation = $0 }, continuation)
}
#endif

/// An `AsyncStream` that never emits and never completes unless cancelled.
public static var never: Self {
Self { _ in }
Expand Down
62 changes: 0 additions & 62 deletions Sources/ConcurrencyExtras/AsyncThrowingStream.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,68 +18,6 @@ extension AsyncThrowingStream where Failure == Error {
}
}

#if swift(<5.9)
/// Constructs and returns a stream along with its backing continuation.
///
/// A back-port of [SE-0388: Convenience Async[Throwing]Stream.makeStream methods][se-0388].
///
/// This is handy for immediately escaping the continuation from an async stream, which
/// typically requires multiple steps:
///
/// ```swift
/// var _continuation: AsyncThrowingStream<Int, Error>.Continuation!
/// let stream = AsyncThrowingStream<Int, Error> { continuation = $0 }
/// let continuation = _continuation!
///
/// // vs.
///
/// let (stream, continuation) = AsyncThrowingStream.makeStream(of: Int.self)
/// ```
///
/// This tool is usually used for tests where we need to supply an async sequence to a
/// dependency endpoint and get access to its continuation so that we can emulate the dependency
/// emitting data. For example, suppose you have a dependency exposing an async sequence for
/// listening to notifications. To test this you can use `makeStream`:
///
/// ```swift
/// func testScreenshots() {
/// let screenshots = AsyncThrowingStream.makeStream(of: Void.self)
///
/// let model = withDependencies {
/// $0.screenshots = { screenshots.stream }
/// } operation: {
/// FeatureModel()
/// }
///
/// XCTAssertEqual(model.screenshotCount, 0)
/// screenshots.continuation.yield() // Simulate a screenshot being taken.
/// XCTAssertEqual(model.screenshotCount, 1)
/// }
/// ```
///
/// > Warning: ⚠️ `AsyncThrowingStream` does not support multiple subscribers, therefore you can
/// > only use this helper to test features that do not subscribe multiple times to the
/// > dependency endpoint.
///
/// [se-0388]: https://github.com/apple/swift-evolution/blob/main/proposals/0388-async-stream-factory.md
///
/// - Parameters:
/// - elementType: The type of element the `AsyncThrowingStream` produces.
/// - failureType: The type of failure the `AsyncThrowingStream` throws.
/// - limit: A Continuation.BufferingPolicy value to set the stream’s buffering behavior. By
/// default, the stream buffers an unlimited number of elements. You can also set the policy
/// to buffer a specified number of oldest or newest elements.
/// - Returns: An `AsyncThrowingStream`.
public static func makeStream(
of elementType: Element.Type = Element.self,
throwing failureType: Failure.Type = Failure.self,
bufferingPolicy limit: Continuation.BufferingPolicy = .unbounded
) -> (stream: Self, continuation: Continuation) {
var continuation: Continuation!
return (Self(elementType, bufferingPolicy: limit) { continuation = $0 }, continuation)
}
#endif

/// An `AsyncThrowingStream` that never emits and never completes unless cancelled.
public static var never: Self {
Self { _ in }
Expand Down
4 changes: 2 additions & 2 deletions Tests/ConcurrencyExtrasTests/AsyncStreamTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

@available(iOS 15, *)
private let sendable: @Sendable () async -> AsyncStream<Void> = {
await NotificationCenter.default
NotificationCenter.default
.notifications(named: UIApplication.userDidTakeScreenshotNotification)
.map { _ in }
.eraseToStream()
Expand All @@ -20,7 +20,7 @@

@available(iOS 15, *)
private let sendableThrowing: @Sendable () async -> AsyncThrowingStream<Void, Error> = {
await NotificationCenter.default
NotificationCenter.default
.notifications(named: UIApplication.userDidTakeScreenshotNotification)
.map { _ in }
.eraseToThrowingStream()
Expand Down
Loading