-
Notifications
You must be signed in to change notification settings - Fork 23
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* Add Wasm/Windows CI * wip * wip * test * wip
- Loading branch information
1 parent
e8af1c3
commit 479750b
Showing
4 changed files
with
214 additions
and
175 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -15,29 +15,60 @@ concurrency: | |
|
||
jobs: | ||
library: | ||
runs-on: macos-13 | ||
name: macOS | ||
strategy: | ||
matrix: | ||
xcode: ['14.3.1'] | ||
config: ['debug', 'release'] | ||
runs-on: macos-13 | ||
steps: | ||
- uses: actions/checkout@v3 | ||
- 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 | ||
|
||
ubuntu-tests: | ||
linux: | ||
name: Linux | ||
strategy: | ||
matrix: | ||
os: [ubuntu-20.04] | ||
config: ['debug', 'release'] | ||
|
||
runs-on: ${{ matrix.os }} | ||
|
||
steps: | ||
- uses: actions/checkout@v3 | ||
- name: Build | ||
run: swift build | ||
- 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 | ||
|
||
windows: | ||
name: Windows | ||
strategy: | ||
matrix: | ||
os: [windows-latest] | ||
config: ['debug', 'release'] | ||
runs-on: ${{ matrix.os }} | ||
steps: | ||
- uses: compnerd/gha-setup-swift@main | ||
with: | ||
branch: swift-5.8-release | ||
tag: 5.8-RELEASE | ||
|
||
- uses: actions/checkout@v3 | ||
- name: Run tests | ||
run: swift build -c ${{ matrix.config }} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,76 +1,78 @@ | ||
import Foundation | ||
#if !os(WASI) && !os(Windows) | ||
import Foundation | ||
|
||
/// Perform an operation on the main serial executor. | ||
/// | ||
/// Some asynchronous code is [notoriously | ||
/// difficult](https://forums.swift.org/t/reliably-testing-code-that-adopts-swift-concurrency/57304) | ||
/// to test in Swift due to how suspension points are processed by the runtime. This function runs | ||
/// all tasks spawned in the given operation serially and deterministically. It makes asynchronous | ||
/// tests faster and less flakey. | ||
/// | ||
/// ```swift | ||
/// await withMainSerialExecutor { | ||
/// // Everything performed in this scope is performed serially... | ||
/// } | ||
/// ``` | ||
/// | ||
/// - Parameter operation: An operation to be performed on the main serial executor. | ||
@MainActor | ||
public func withMainSerialExecutor( | ||
@_implicitSelfCapture operation: @MainActor @Sendable () async throws -> Void | ||
) async rethrows { | ||
let didUseMainSerialExecutor = uncheckedUseMainSerialExecutor | ||
defer { uncheckedUseMainSerialExecutor = didUseMainSerialExecutor } | ||
uncheckedUseMainSerialExecutor = true | ||
try await operation() | ||
} | ||
/// Perform an operation on the main serial executor. | ||
/// | ||
/// Some asynchronous code is [notoriously | ||
/// difficult](https://forums.swift.org/t/reliably-testing-code-that-adopts-swift-concurrency/57304) | ||
/// to test in Swift due to how suspension points are processed by the runtime. This function runs | ||
/// all tasks spawned in the given operation serially and deterministically. It makes asynchronous | ||
/// tests faster and less flakey. | ||
/// | ||
/// ```swift | ||
/// await withMainSerialExecutor { | ||
/// // Everything performed in this scope is performed serially... | ||
/// } | ||
/// ``` | ||
/// | ||
/// - Parameter operation: An operation to be performed on the main serial executor. | ||
@MainActor | ||
public func withMainSerialExecutor( | ||
@_implicitSelfCapture operation: @MainActor @Sendable () async throws -> Void | ||
) async rethrows { | ||
let didUseMainSerialExecutor = uncheckedUseMainSerialExecutor | ||
defer { uncheckedUseMainSerialExecutor = didUseMainSerialExecutor } | ||
uncheckedUseMainSerialExecutor = true | ||
try await operation() | ||
} | ||
|
||
/// Perform an operation on the main serial executor. | ||
/// | ||
/// A synchronous version of ``withMainSerialExecutor(operation:)-79jpc`` that can be used in | ||
/// `XCTestCase.invokeTest` to ensure all async tests are performed serially: | ||
/// | ||
/// ```swift | ||
/// class BaseTestCase: XCTestCase { | ||
/// override func invokeTest() { | ||
/// withMainSerialExecutor { | ||
/// super.invokeTest() | ||
/// } | ||
/// } | ||
/// } | ||
/// ``` | ||
/// | ||
/// - Parameter operation: An operation to be performed on the main serial executor. | ||
public func withMainSerialExecutor( | ||
@_implicitSelfCapture operation: () throws -> Void | ||
) rethrows { | ||
let didUseMainSerialExecutor = uncheckedUseMainSerialExecutor | ||
defer { uncheckedUseMainSerialExecutor = didUseMainSerialExecutor } | ||
uncheckedUseMainSerialExecutor = true | ||
try operation() | ||
} | ||
/// Perform an operation on the main serial executor. | ||
/// | ||
/// A synchronous version of ``withMainSerialExecutor(operation:)-79jpc`` that can be used in | ||
/// `XCTestCase.invokeTest` to ensure all async tests are performed serially: | ||
/// | ||
/// ```swift | ||
/// class BaseTestCase: XCTestCase { | ||
/// override func invokeTest() { | ||
/// withMainSerialExecutor { | ||
/// super.invokeTest() | ||
/// } | ||
/// } | ||
/// } | ||
/// ``` | ||
/// | ||
/// - Parameter operation: An operation to be performed on the main serial executor. | ||
public func withMainSerialExecutor( | ||
@_implicitSelfCapture operation: () throws -> Void | ||
) rethrows { | ||
let didUseMainSerialExecutor = uncheckedUseMainSerialExecutor | ||
defer { uncheckedUseMainSerialExecutor = didUseMainSerialExecutor } | ||
uncheckedUseMainSerialExecutor = true | ||
try operation() | ||
} | ||
|
||
/// Overrides Swift's global executor with the main serial executor in an unchecked fashion. | ||
/// | ||
/// > Warning: When set to `true`, all tasks will be enqueued on the main serial executor till set | ||
/// > back to `false`. Consider using ``withMainSerialExecutor(operation:)-79jpc``, instead, which | ||
/// > scopes this work to the duration of a given operation. | ||
public var uncheckedUseMainSerialExecutor: Bool { | ||
get { swift_task_enqueueGlobal_hook != nil } | ||
set { | ||
swift_task_enqueueGlobal_hook = | ||
newValue | ||
? { job, _ in MainActor.shared.enqueue(job) } | ||
: nil | ||
/// Overrides Swift's global executor with the main serial executor in an unchecked fashion. | ||
/// | ||
/// > Warning: When set to `true`, all tasks will be enqueued on the main serial executor till set | ||
/// > back to `false`. Consider using ``withMainSerialExecutor(operation:)-79jpc``, instead, which | ||
/// > scopes this work to the duration of a given operation. | ||
public var uncheckedUseMainSerialExecutor: Bool { | ||
get { swift_task_enqueueGlobal_hook != nil } | ||
set { | ||
swift_task_enqueueGlobal_hook = | ||
newValue | ||
? { job, _ in MainActor.shared.enqueue(job) } | ||
: nil | ||
} | ||
} | ||
} | ||
|
||
private typealias Original = @convention(thin) (UnownedJob) -> Void | ||
private typealias Hook = @convention(thin) (UnownedJob, Original) -> Void | ||
private typealias Original = @convention(thin) (UnownedJob) -> Void | ||
private typealias Hook = @convention(thin) (UnownedJob, Original) -> Void | ||
|
||
private var swift_task_enqueueGlobal_hook: Hook? { | ||
get { _swift_task_enqueueGlobal_hook.pointee } | ||
set { _swift_task_enqueueGlobal_hook.pointee = newValue } | ||
} | ||
private let _swift_task_enqueueGlobal_hook: UnsafeMutablePointer<Hook?> = | ||
dlsym(dlopen(nil, 0), "swift_task_enqueueGlobal_hook").assumingMemoryBound(to: Hook?.self) | ||
private var swift_task_enqueueGlobal_hook: Hook? { | ||
get { _swift_task_enqueueGlobal_hook.pointee } | ||
set { _swift_task_enqueueGlobal_hook.pointee = newValue } | ||
} | ||
private let _swift_task_enqueueGlobal_hook: UnsafeMutablePointer<Hook?> = | ||
dlsym(dlopen(nil, 0), "swift_task_enqueueGlobal_hook").assumingMemoryBound(to: Hook?.self) | ||
#endif |
Oops, something went wrong.