diff --git a/.github/workflows/validate-all.yml b/.github/workflows/validate-all.yml
index 26d409d86..e314f00cc 100644
--- a/.github/workflows/validate-all.yml
+++ b/.github/workflows/validate-all.yml
@@ -8,48 +8,54 @@ on:
branches: [main]
env:
- IOS_PLATFORM: iOS Simulator
- IOS_DEVICE: iPhone 15
- IOS_VERSION: 17.4
+ XCODE_VERSION: "26.0"
jobs:
- # TODO: enable when swiftlint supports a linux binary in its artifact bundle
- # lint:
- # name: Lint
- # timeout-minutes: 2
- # runs-on: ubuntu-latest
- # defaults:
- # run:
- # working-directory: ./Vault
- #
- # steps:
- # - uses: actions/checkout@v4
- # - name: Lint Sources
- # run: make lint
+ lint:
+ name: Lint
+ timeout-minutes: 2
+ runs-on: macos-26
+ defaults:
+ run:
+ working-directory: ./Vault
- # build:
- # name: Build
- # timeout-minutes: 5
- # runs-on: macos-14
- #
- # steps:
- # - uses: actions/checkout@v4
- # - run: sudo xcode-select -s /Applications/Xcode_15.3.app/Contents/Developer
- # - name: Build App
- # run: xcodebuild -workspace Vault.xcworkspace -scheme VaultApp -destination 'platform=${{ env.IOS_PLATFORM }},name=${{ env.IOS_DEVICE }},OS=${{ env.IOS_VERSION }}' -skipMacroValidation -quiet build
- #
+ steps:
+ - uses: actions/checkout@v4
+ - run: sudo xcode-select -s /Applications/Xcode_${{ env.XCODE_VERSION }}.app/Contents/Developer
+
+ - name: Cache SPM Dependencies
+ uses: actions/cache@v4
+ with:
+ path: |
+ ~/Library/Caches/org.swift.swiftpm/repositories
+ Vault/.build
+ key: ${{ runner.os }}-spm-lint-${{ hashFiles('Vault/Package.resolved') }}
+ restore-keys: |
+ ${{ runner.os }}-spm-lint-
+
+ - name: Check Linting & Formatting
+ run: make lint
+
+ # Don't test for now to save CI time
# test:
# name: Test
- # timeout-minutes: 30
- # runs-on: ubuntu-latest
- # # runs-on: macos-14
+ # timeout-minutes: 10
+ # runs-on: macos-26
#
# steps:
- # # We currently don't run tests in CI due to cost.
- # # This can be re-enabled when the repo is made public!
- # - name: Skip Testing
- # run: true
# - uses: actions/checkout@v4
- # - run: sudo xcode-select -s /Applications/Xcode_15.3.app/Contents/Developer
- # - name: Run all Tests
- # run: xcodebuild -workspace Vault.xcworkspace -scheme CI_iOS -destination 'platform=${{ env.IOS_PLATFORM }},name=${{ env.IOS_DEVICE }},OS=${{ env.IOS_VERSION }}' -skipMacroValidation -quiet test
+ # - run: sudo xcode-select -s /Applications/Xcode_${{ env.XCODE_VERSION }}.app/Contents/Developer
+ #
+ # - name: Cache SPM Dependencies
+ # uses: actions/cache@v4
+ # with:
+ # path: ~/Library/Caches/org.swift.swiftpm/repositories
+ # key: ${{ runner.os }}-spm-${{ hashFiles('Vault/Package.resolved') }}
+ # restore-keys: |
+ # ${{ runner.os }}-spm-
+ #
+ # - name: Clear SPM Artifacts
+ # run: rm -rf ~/Library/Caches/org.swift.swiftpm/artifacts
+ #
+ # - name: Test CI_macOS
+ # run: xcodebuild test -workspace Vault.xcworkspace -scheme CI_macOS -skipMacroValidation -skipPackagePluginValidation
diff --git a/README.md b/README.md
index bd36b4ed9..131787fe6 100644
--- a/README.md
+++ b/README.md
@@ -11,7 +11,6 @@ There is purposely no automatic or online backup, so you never need to worry abo
There's a few ways that you can use Vault to store your data:
1. Super secret data
-
- Store data you really don't want to be accessed in encrypted notes, like cryptocurrency private keys. Hide them and add a killcode so, if under duress, you can wipe them with plausible deniability. Restore from a backup when you get home.
2. Store OTP codes
diff --git a/Vault/.swiftpm/xcode/xcshareddata/xcschemes/CI_iOS.xcscheme b/Vault/.swiftpm/xcode/xcshareddata/xcschemes/CI_iOS.xcscheme
index 90a9c4a1a..22f8cb2e7 100644
--- a/Vault/.swiftpm/xcode/xcshareddata/xcschemes/CI_iOS.xcscheme
+++ b/Vault/.swiftpm/xcode/xcshareddata/xcschemes/CI_iOS.xcscheme
@@ -28,6 +28,9 @@
reference = "container:TestPlans/CI/iOSAllTests.xctestplan"
default = "YES">
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Vault/Makefile b/Vault/Makefile
index 913182f13..cd099e389 100644
--- a/Vault/Makefile
+++ b/Vault/Makefile
@@ -6,10 +6,12 @@ benchmark-keygen:
.PHONY: format
format:
+ swift package plugin --allow-writing-to-package-directory swiftlint --fix --quiet ./Sources
swift package --allow-writing-to-package-directory format --sources=./
.PHONY: lint
lint:
+ swift package plugin swiftlint --strict --quiet ./Sources
swift package --allow-writing-to-package-directory format --lint --sources=./
.PHONY: clean
diff --git a/Vault/Package.swift b/Vault/Package.swift
index 20f12b68e..c183de1d5 100644
--- a/Vault/Package.swift
+++ b/Vault/Package.swift
@@ -276,20 +276,18 @@ let package = Package(
capability: .command(
intent: .custom(
verb: "format",
- description: "Formats Swift source files using swiftformat and swiftlint"
+ description: "Formats Swift source files using swiftformat only"
),
permissions: [.writeToPackageDirectory(reason: "Format source code")]
- )
+ ),
+ dependencies: [
+ "swiftformat",
+ ]
),
.binaryTarget(
name: "swiftformat",
url: "https://github.com/nicklockwood/SwiftFormat/releases/download/\(swiftFormatVersion)/swiftformat.artifactbundle.zip",
checksum: swiftFormatChecksum
),
- .binaryTarget(
- name: "swiftlint",
- url: "https://github.com/realm/SwiftLint/releases/download/\(swiftLintVersion)/SwiftLintBinary-macos.artifactbundle.zip",
- checksum: swiftLintChecksum
- ),
]
)
diff --git a/Vault/Plugins/FormatLint/Plugin.swift b/Vault/Plugins/FormatLint/Plugin.swift
index 3c2f8a43d..d86f29373 100644
--- a/Vault/Plugins/FormatLint/Plugin.swift
+++ b/Vault/Plugins/FormatLint/Plugin.swift
@@ -9,8 +9,6 @@ struct FormatLintPlugin: CommandPlugin {
let formatLintContext = try makeFormatLintContext(context: context, arguments: arguments)
let start = Date()
- // Lint before formatting so any formatting that results in lint errors is surfaced and we can address it.
- try formatLintContext.runSwiftLint()
try formatLintContext.runSwiftFormat()
let end = Date()
let elapsed = end.timeIntervalSince(start)
@@ -32,7 +30,6 @@ struct FormatLintPlugin: CommandPlugin {
.format
}
return try FormatLintContext(
- swiftlint: context.tool(named: "swiftlint"),
swiftformat: context.tool(named: "swiftformat"),
workDirectory: context.pluginWorkDirectoryURL,
swiftSourcesDirectory: swiftSources,
@@ -42,40 +39,12 @@ struct FormatLintPlugin: CommandPlugin {
}
struct FormatLintContext {
- var swiftlint: PluginContext.Tool
var swiftformat: PluginContext.Tool
var workDirectory: URL
var swiftSourcesDirectory: String
var action: Action
}
-extension FormatLintContext {
- func makeSwiftLintArgs() -> [String] {
- var swiftLintArguments = [String]()
- swiftLintArguments += ["--cache-path", workDirectory.appending(path: "swiftlint.cache").path()]
- swiftLintArguments += ["--quiet"]
- switch action {
- case .format:
- swiftLintArguments += ["--fix"]
- case .lint:
- swiftLintArguments += ["--strict"]
- }
- swiftLintArguments += [swiftSourcesDirectory]
- return swiftLintArguments
- }
-
- func runSwiftLint() throws {
- print("🔍 swiftlint: \(action.swiftLintVerb.lowercased())")
- try runProcess(
- url: swiftlint.url,
- arguments: makeSwiftLintArgs(),
- exitCodeHandler: swiftLintExitCodeHandler(code:)
- )
- }
-}
-
-// MARK: - swiftformat
-
extension FormatLintContext {
func makeSwiftFormatArgs() -> [String] {
var swiftFormatArguments = [String]()
@@ -110,13 +79,6 @@ enum Action {
case .lint: "Checking"
}
}
-
- var swiftLintVerb: String {
- switch self {
- case .format: "Fixing"
- case .lint: "Linting"
- }
- }
}
enum CommandError: Error {
@@ -149,13 +111,3 @@ func swiftFormatExitCodeHandler(code: Int32) throws {
throw CommandError.unknownError(exitCode: code)
}
}
-
-func swiftLintExitCodeHandler(code: Int32) throws {
- switch code {
- case 0:
- print("☑️ swiftlint done")
- default:
- print("❌ swiftlint failure")
- throw CommandError.exitWithError
- }
-}
diff --git a/Vault/Sources/TestHelpers/PDFDocument+Snapshot.swift b/Vault/Sources/TestHelpers/PDFDocument+Snapshot.swift
index c8b2c64a1..4e95883d0 100644
--- a/Vault/Sources/TestHelpers/PDFDocument+Snapshot.swift
+++ b/Vault/Sources/TestHelpers/PDFDocument+Snapshot.swift
@@ -1,3 +1,4 @@
+#if canImport(UIKit)
import Foundation
import PDFKit
import SnapshotTesting
@@ -36,3 +37,5 @@ extension PDFDocument {
}
}
}
+
+#endif
diff --git a/Vault/Sources/TestHelpers/SuspendForever.swift b/Vault/Sources/TestHelpers/SuspendForever.swift
index 633031900..01cc5d2c5 100644
--- a/Vault/Sources/TestHelpers/SuspendForever.swift
+++ b/Vault/Sources/TestHelpers/SuspendForever.swift
@@ -5,10 +5,10 @@ import Foundation
/// This is achieved by awaiting on a stream that never yields any values.
///
/// - throws: `CancellationError` if the task this is in is cancelled.
-public func suspendForever() async throws -> Never {
+public func suspendForever() async throws {
let stream = AsyncStream { _ in }
for await _ in stream {
- return fatalError("Unreachable")
+ fatalError("Unreachable")
}
// The stream will only exit without a value in the case that it's been cancelled.
// Propagate the cancellation.
diff --git a/Vault/Sources/VaultFeed/Presentation/Backup/BackupImportFlowViewModel.swift b/Vault/Sources/VaultFeed/Presentation/Backup/BackupImportFlowViewModel.swift
index 060912ad9..ceb4b2ef0 100644
--- a/Vault/Sources/VaultFeed/Presentation/Backup/BackupImportFlowViewModel.swift
+++ b/Vault/Sources/VaultFeed/Presentation/Backup/BackupImportFlowViewModel.swift
@@ -105,7 +105,7 @@ public final class BackupImportFlowViewModel {
case let .readyToImport(applicationPayload):
payloadState = .ready(applicationPayload, UUID())
}
- } catch let error as LocalizedError {
+ } catch let error as any LocalizedError {
payloadState = .error(.init(localizedError: error))
} catch {
payloadState = .error(PresentationError(
@@ -140,7 +140,7 @@ public final class BackupImportFlowViewModel {
try await dataModel.importOverride(payload: payload)
}
importState = .success
- } catch let error as LocalizedError {
+ } catch let error as any LocalizedError {
importState = .error(.init(localizedError: error))
} catch {
importState = .error(PresentationError(
diff --git a/Vault/Sources/VaultFeed/Presentation/Backup/BackupKeyDecryptorViewModel.swift b/Vault/Sources/VaultFeed/Presentation/Backup/BackupKeyDecryptorViewModel.swift
index 347a3c866..b99ed0d17 100644
--- a/Vault/Sources/VaultFeed/Presentation/Backup/BackupKeyDecryptorViewModel.swift
+++ b/Vault/Sources/VaultFeed/Presentation/Backup/BackupKeyDecryptorViewModel.swift
@@ -91,7 +91,7 @@ public final class BackupKeyDecryptorViewModel {
)
decryptionKeyState = .validDecryptionKey
decryptedVaultSubject.send(vaultApplicationPayload)
- } catch let error as LocalizedError {
+ } catch let error as any LocalizedError {
decryptionKeyState = .error(.init(localizedError: error))
} catch {
decryptionKeyState = .error(PresentationError(
diff --git a/Vault/Sources/VaultFeed/Presentation/Detail/EncryptedItemDetailViewModel.swift b/Vault/Sources/VaultFeed/Presentation/Detail/EncryptedItemDetailViewModel.swift
index fbb3a5430..3da23f946 100644
--- a/Vault/Sources/VaultFeed/Presentation/Detail/EncryptedItemDetailViewModel.swift
+++ b/Vault/Sources/VaultFeed/Presentation/Detail/EncryptedItemDetailViewModel.swift
@@ -81,7 +81,7 @@ public final class EncryptedItemDetailViewModel {
case let .decrypted(item):
state = .decrypted(item, generatedPassword)
}
- } catch let localized as LocalizedError {
+ } catch let localized as any LocalizedError {
state = .decryptionError(PresentationError(localizedError: localized))
} catch {
state = .decryptionError(PresentationError(
diff --git a/Vault/Sources/VaultFeed/Presentation/OTPCode/OTPCodeTimerUpdater.swift b/Vault/Sources/VaultFeed/Presentation/OTPCode/OTPCodeTimerUpdater.swift
index c566e432b..2d6daf757 100644
--- a/Vault/Sources/VaultFeed/Presentation/OTPCode/OTPCodeTimerUpdater.swift
+++ b/Vault/Sources/VaultFeed/Presentation/OTPCode/OTPCodeTimerUpdater.swift
@@ -14,7 +14,7 @@ public protocol OTPCodeTimerUpdater: AnyObject {
/// Controller for producing timers for a given code, according to a clock.
@MainActor
-public final class OTPCodeTimerUpdaterImpl: OTPCodeTimerUpdater, Sendable {
+public final class OTPCodeTimerUpdaterImpl: OTPCodeTimerUpdater {
private let timerStateSubject: CurrentValueSubject
private let period: UInt64
private let timerTask = SharedMutex?>(nil)
diff --git a/Vault/Sources/VaultFeed/Storage/VaultDataModel.swift b/Vault/Sources/VaultFeed/Storage/VaultDataModel.swift
index ac60b7866..9d0b3d8eb 100644
--- a/Vault/Sources/VaultFeed/Storage/VaultDataModel.swift
+++ b/Vault/Sources/VaultFeed/Storage/VaultDataModel.swift
@@ -12,7 +12,7 @@ import VaultKeygen
/// This is isolated to the main actor for the purposes of UI interop.
@MainActor
@Observable
-public final class VaultDataModel: Sendable {
+public final class VaultDataModel {
public enum State {
case base, loaded, loading
}
diff --git a/Vault/Sources/VaultFeed/Storage/VaultStore/SwiftData/PersistedLocalVaultStore.swift b/Vault/Sources/VaultFeed/Storage/VaultStore/SwiftData/PersistedLocalVaultStore.swift
index 1f3d7145f..13ca0d282 100644
--- a/Vault/Sources/VaultFeed/Storage/VaultStore/SwiftData/PersistedLocalVaultStore.swift
+++ b/Vault/Sources/VaultFeed/Storage/VaultStore/SwiftData/PersistedLocalVaultStore.swift
@@ -71,17 +71,14 @@ extension PersistedLocalVaultStore: VaultStoreReader {
return .true
} else {
let searchingTagIds = tags.map(\.id).reducedToSet()
- // Returns the number of tags matched by this item.
- let tagsMatchingSearch = #Expression { item in
- item.tags.filter { tag in
- searchingTagIds.contains(tag.id)
- }.count
- }
- // Performs an "AND" query by checking if the number of tags matched equals
- // the number of tags we are searching for.
- let searchingTagsCount = searchingTagIds.count
+ // Performs an "AND" query by checking if all searched tags are present in the item's tags.
+ // We convert the set to an array to use filter, which is supported in SwiftData predicates.
+ // An item matches if the count of its tags that match our search equals the search count.
+ let searchingTagsArray = Array(searchingTagIds)
return #Predicate { item in
- tagsMatchingSearch.evaluate(item) == searchingTagsCount
+ item.tags.count(where: { tag in
+ searchingTagsArray.contains(tag.id)
+ }) == searchingTagsArray.count
}
}
}
diff --git a/Vault/Sources/VaultKeygenSpeedtest/Speedtest.swift b/Vault/Sources/VaultKeygenSpeedtest/Speedtest.swift
index c3deb8b27..b044d2848 100644
--- a/Vault/Sources/VaultKeygenSpeedtest/Speedtest.swift
+++ b/Vault/Sources/VaultKeygenSpeedtest/Speedtest.swift
@@ -15,7 +15,7 @@ import VaultKeygen
@main
struct KeygenSpeedtest {
- public static func main() throws {
+ static func main() throws {
print("🚧 Build configuration:", buildConfigString())
try benchmark(keyDeriver: VaultKeyDeriver.Item.Fast.v1, description: "Item Fast")
diff --git a/Vault/Sources/VaultiOS/Views/TimerBar/CodeTimerHorizontalBarView.swift b/Vault/Sources/VaultiOS/Views/TimerBar/CodeTimerHorizontalBarView.swift
index 0ea13e2e7..b89241a16 100644
--- a/Vault/Sources/VaultiOS/Views/TimerBar/CodeTimerHorizontalBarView.swift
+++ b/Vault/Sources/VaultiOS/Views/TimerBar/CodeTimerHorizontalBarView.swift
@@ -49,21 +49,19 @@ struct CodeTimerHorizontalBarView: View {
resetTimerBarAnimation = .init(qos: .userInteractive) {
withAnimation(
.linear(duration: animateReset ? 0.15 : 0),
- completionCriteria: .removed,
- {
- currentFractionCompleted = timerState.animationState.initialFraction(currentTime: clock.currentTime)
- },
- completion: {
- if case let .animate(state) = timerState.animationState {
- timerAnimation = .init(qos: .userInteractive) {
- withAnimation(.linear(duration: state.remainingTime(at: clock.currentTime))) {
- currentFractionCompleted = 0
- }
+ completionCriteria: .removed
+ ) {
+ currentFractionCompleted = timerState.animationState.initialFraction(currentTime: clock.currentTime)
+ } completion: {
+ if case let .animate(state) = timerState.animationState {
+ timerAnimation = .init(qos: .userInteractive) {
+ withAnimation(.linear(duration: state.remainingTime(at: clock.currentTime))) {
+ currentFractionCompleted = 0
}
- timerAnimation?.perform()
}
+ timerAnimation?.perform()
}
- )
+ }
}
resetTimerBarAnimation?.perform()
}
diff --git a/Vault/Sources/VaultiOSAutofill/Views/VaultAutofillConfigurationView.swift b/Vault/Sources/VaultiOSAutofill/Views/VaultAutofillConfigurationView.swift
index 09abad973..a8625f753 100644
--- a/Vault/Sources/VaultiOSAutofill/Views/VaultAutofillConfigurationView.swift
+++ b/Vault/Sources/VaultiOSAutofill/Views/VaultAutofillConfigurationView.swift
@@ -4,11 +4,11 @@ import VaultiOS
struct VaultAutofillConfigurationView: View {
@State private var viewModel: VaultAutofillConfigurationViewModel
- public init(viewModel: VaultAutofillConfigurationViewModel) {
+ init(viewModel: VaultAutofillConfigurationViewModel) {
self.viewModel = viewModel
}
- public var body: some View {
+ var body: some View {
ScrollView {
container
.padding(.vertical, 16)
diff --git a/Vault/TestPlans/CI/macOS_SupportedTests.xctestplan b/Vault/TestPlans/CI/macOS_SupportedTests.xctestplan
new file mode 100644
index 000000000..2051c455c
--- /dev/null
+++ b/Vault/TestPlans/CI/macOS_SupportedTests.xctestplan
@@ -0,0 +1,52 @@
+{
+ "configurations" : [
+ {
+ "id" : "D213A255-37DA-4E13-8AB8-3AD0E9C299FE",
+ "name" : "Configuration 1",
+ "options" : {
+
+ }
+ }
+ ],
+ "defaultOptions" : {
+ "testTimeoutsEnabled" : true
+ },
+ "testTargets" : [
+ {
+ "target" : {
+ "containerPath" : "container:",
+ "identifier" : "VaultCoreTests",
+ "name" : "VaultCoreTests"
+ }
+ },
+ {
+ "target" : {
+ "containerPath" : "container:",
+ "identifier" : "FoundationExtensionsTests",
+ "name" : "FoundationExtensionsTests"
+ }
+ },
+ {
+ "target" : {
+ "containerPath" : "container:",
+ "identifier" : "CryptoEngineTests",
+ "name" : "CryptoEngineTests"
+ }
+ },
+ {
+ "target" : {
+ "containerPath" : "container:",
+ "identifier" : "VaultKeygenTests",
+ "name" : "VaultKeygenTests"
+ }
+ },
+ {
+ "target" : {
+ "containerPath" : "container:",
+ "identifier" : "VaultKeygenSpeedtestCompileTests",
+ "name" : "VaultKeygenSpeedtestCompileTests"
+ }
+ }
+ ],
+ "version" : 1
+}
diff --git a/Vault/Tests/CryptoEngineTests/DataHelpersTests.swift b/Vault/Tests/CryptoEngineTests/DataHelpersTests.swift
index 6e47f358c..79a64a983 100644
--- a/Vault/Tests/CryptoEngineTests/DataHelpersTests.swift
+++ b/Vault/Tests/CryptoEngineTests/DataHelpersTests.swift
@@ -28,12 +28,12 @@ struct DataHelpersTests {
@Test
func int64ToData_interpretsAsLittleEndian() {
let number: UInt64 = 1
- #expect(number.data.bytes == [1, 0, 0, 0, 0, 0, 0, 0])
+ #expect(Array(number.data) == [1, 0, 0, 0, 0, 0, 0, 0])
}
@Test
func byteString_interpretsUTF8StringValues() {
let value = Data(byteString: "1234")
- #expect(value.bytes == [49, 50, 51, 52])
+ #expect(Array(value) == [49, 50, 51, 52])
}
}
diff --git a/Vault/Tests/FoundationExtensionsTests/DefaultsStoredTests.swift b/Vault/Tests/FoundationExtensionsTests/DefaultsStoredTests.swift
index 24a31daff..4129a0305 100644
--- a/Vault/Tests/FoundationExtensionsTests/DefaultsStoredTests.swift
+++ b/Vault/Tests/FoundationExtensionsTests/DefaultsStoredTests.swift
@@ -33,7 +33,7 @@ final class DefaultsStoredTests {
}
@Test
- func test_wrappedValue_setsValueInDefaults() throws {
+ func wrappedValue_setsValueInDefaults() throws {
let key: Key = .init("test3")
let coolNumberInitial = 4567
try defaults.set(coolNumberInitial, for: key)
diff --git a/Vault/Tests/FoundationExtensionsTests/PendingValueTests.swift b/Vault/Tests/FoundationExtensionsTests/PendingValueTests.swift
index 8f8e82fbe..c0566a398 100644
--- a/Vault/Tests/FoundationExtensionsTests/PendingValueTests.swift
+++ b/Vault/Tests/FoundationExtensionsTests/PendingValueTests.swift
@@ -218,14 +218,14 @@ extension PendingValueTests {
/// Without this, you might acidentally call `fulfill`/`reject` before await, and thus the value will be cached.
private func awaitValueInBackground(
on sut: SUT,
- action: () async -> Void
+ action: @Sendable () async -> Void
) async throws -> Result {
let startedWaiting = Pending.signal()
let finishedWaiting = Pending.signal()
- var result: Result?
let task = Task.detached(priority: .high) {
await startedWaiting.fulfill()
+ let result: Result
do {
let value = try await sut.wait()
result = .success(value)
@@ -233,6 +233,7 @@ extension PendingValueTests {
result = .failure(error)
}
await finishedWaiting.fulfill()
+ return result
}
try await startedWaiting.wait(timeout: .seconds(1))
@@ -242,8 +243,8 @@ extension PendingValueTests {
try await finishedWaiting.wait(timeout: .seconds(1))
- task.cancel()
- return try #require(result)
+ defer { task.cancel() }
+ return await task.value
}
private func awaitNoValueProduced(on sut: SUT) async {
diff --git a/Vault/Tests/VaultCoreTests/OTPAuthDigitsTests.swift b/Vault/Tests/VaultCoreTests/OTPAuthDigitsTests.swift
index 1bf20b527..6be417605 100644
--- a/Vault/Tests/VaultCoreTests/OTPAuthDigitsTests.swift
+++ b/Vault/Tests/VaultCoreTests/OTPAuthDigitsTests.swift
@@ -4,7 +4,7 @@ import VaultCore
struct OTPAuthDigitsTests {
@Test
- func test_description_encodesToSimpleDigits() {
+ func description_encodesToSimpleDigits() {
let digits = OTPAuthDigits(value: 123)
#expect("\(digits)" == "123")
diff --git a/Vault/Tests/VaultCoreTests/URI/OTPAuthURIEncoderTests.swift b/Vault/Tests/VaultCoreTests/URI/OTPAuthURIEncoderTests.swift
index f9038578b..90a9cf2d8 100644
--- a/Vault/Tests/VaultCoreTests/URI/OTPAuthURIEncoderTests.swift
+++ b/Vault/Tests/VaultCoreTests/URI/OTPAuthURIEncoderTests.swift
@@ -6,7 +6,7 @@ struct OTPAuthURIEncoderTests {
let sut = OTPAuthURIEncoder()
@Test
- func test_encodeScheme_isOtpauth() throws {
+ func encodeScheme_isOtpauth() throws {
let code = makeCode(type: .totp())
let encoded = try sut.encode(code: code)
diff --git a/Vault/Tests/VaultFeedTests/CodeScanner/BackupImportScanningHandlerTests.swift b/Vault/Tests/VaultFeedTests/CodeScanner/BackupImportScanningHandlerTests.swift
index 008049bfc..db43fffa6 100644
--- a/Vault/Tests/VaultFeedTests/CodeScanner/BackupImportScanningHandlerTests.swift
+++ b/Vault/Tests/VaultFeedTests/CodeScanner/BackupImportScanningHandlerTests.swift
@@ -94,7 +94,7 @@ struct BackupImportScanningHandlerTests {
}
@Test
- func test_decodeInvalidFullDataEndsWithUnrecoverableError() throws {
+ func decodeInvalidFullDataEndsWithUnrecoverableError() throws {
let result1 = sut.decode(data: """
{
"G":{"ID":10,"N":2,"I":0},