Skip to content

Commit ce5c0ab

Browse files
committed
tests++
1 parent 5fe292a commit ce5c0ab

File tree

7 files changed

+287
-0
lines changed

7 files changed

+287
-0
lines changed
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import XCTest
5+
@testable import CornucopiaCore
6+
7+
final class ArrayHexTests: XCTestCase {
8+
9+
func testHexDecodedStringProducesUppercaseOutput() {
10+
11+
let bytes: [UInt8] = [0xDE, 0xAD, 0xBE, 0xEF]
12+
let hex = deprecatedHexString(from: bytes)
13+
XCTAssertEqual(hex, "DEADBEEF")
14+
}
15+
16+
func testHexDecodedStringWithSpacesInsertsDelimiter() {
17+
18+
let bytes: [UInt8] = [0x00, 0xAB, 0xCD]
19+
let hexWithSpaces = deprecatedHexStringWithSpaces(from: bytes)
20+
XCTAssertEqual(hexWithSpaces, "00 AB CD")
21+
}
22+
23+
@available(*, deprecated)
24+
private func deprecatedHexString(from bytes: [UInt8]) -> String { bytes.CC_hexDecodedString }
25+
26+
@available(*, deprecated)
27+
private func deprecatedHexStringWithSpaces(from bytes: [UInt8]) -> String { bytes.CC_hexDecodedStringWithSpaces }
28+
}
Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import XCTest
5+
@testable import CornucopiaCore
6+
7+
final class AsyncSequenceCollectTests: XCTestCase {
8+
9+
func testCollectReturnsAllElements() async throws {
10+
11+
let expected = Array(0..<5)
12+
let stream = AsyncStream<Int> { continuation in
13+
expected.forEach { continuation.yield($0) }
14+
continuation.finish()
15+
}
16+
17+
let collected = try await stream.CC_collect()
18+
XCTAssertEqual(collected, expected)
19+
}
20+
21+
func testCollectPropagatesErrors() async {
22+
23+
enum SampleError: Error {
24+
case boom
25+
}
26+
27+
let stream = AsyncThrowingStream<Int, Error> { continuation in
28+
continuation.yield(42)
29+
continuation.finish(throwing: SampleError.boom)
30+
}
31+
32+
do {
33+
_ = try await stream.CC_collect()
34+
XCTFail("Expected CC_collect to rethrow the original error.")
35+
} catch {
36+
guard case SampleError.boom = error else {
37+
return XCTFail("Unexpected error: \\(error)")
38+
}
39+
}
40+
}
41+
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import XCTest
5+
@testable import CornucopiaCore
6+
7+
final class BinaryIntegerParityTests: XCTestCase {
8+
9+
func testParityInitializerDetectsEvenAndOddValues() {
10+
11+
XCTAssertEqual(Cornucopia.Core.Parity(0), .even)
12+
XCTAssertEqual(Cornucopia.Core.Parity(1), .odd)
13+
XCTAssertEqual(Cornucopia.Core.Parity(2), .even)
14+
XCTAssertEqual(Cornucopia.Core.Parity(-3), .odd)
15+
}
16+
17+
func testBinaryIntegerExtensionBridgesToParity() {
18+
19+
XCTAssertEqual(42.CC_parity, .even)
20+
XCTAssertEqual(17.CC_parity, .odd)
21+
XCTAssertEqual((-96).CC_parity, .even)
22+
}
23+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import XCTest
5+
@testable import CornucopiaCore
6+
7+
final class CaseIterableRandomElementTests: XCTestCase {
8+
9+
private enum SampleEnum: CaseIterable {
10+
case foo
11+
case bar
12+
case baz
13+
}
14+
15+
private enum SingleCaseEnum: CaseIterable {
16+
case only
17+
}
18+
19+
func testRandomElementReturnsMemberOfAllCases() {
20+
21+
for _ in 0..<50 {
22+
guard let element = SampleEnum.CC_randomElement else {
23+
return XCTFail("Expected a random element for non-empty CaseIterable type.")
24+
}
25+
XCTAssertTrue(SampleEnum.allCases.contains(element))
26+
}
27+
}
28+
29+
func testRandomElementForSingleCaseEnumAlwaysReturnsThatCase() {
30+
XCTAssertEqual(SingleCaseEnum.CC_randomElement, .only)
31+
}
32+
}
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import XCTest
5+
@testable import CornucopiaCore
6+
7+
final class CollectionSortByKeyPathTests: XCTestCase {
8+
9+
struct Payload: Equatable {
10+
let value: Int
11+
let label: String
12+
}
13+
14+
func testSortByKeyPathAscending() {
15+
16+
let payloads = [
17+
Payload(value: 2, label: "b"),
18+
Payload(value: 1, label: "a"),
19+
Payload(value: 3, label: "c"),
20+
]
21+
22+
let sorted = payloads.CC_sorted(by: \.value, <)
23+
XCTAssertEqual(sorted.map(\.value), [1, 2, 3])
24+
}
25+
26+
func testSortByKeyPathDescendingWithCustomComparator() {
27+
28+
let payloads = [
29+
Payload(value: 5, label: "middle"),
30+
Payload(value: 1, label: "low"),
31+
Payload(value: 10, label: "high"),
32+
]
33+
34+
let sorted = payloads.CC_sorted(by: \.value) { lhs, rhs in lhs > rhs }
35+
XCTAssertEqual(sorted.map(\.value), [10, 5, 1])
36+
}
37+
}
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import CoreFoundation
5+
import XCTest
6+
@testable import CornucopiaCore
7+
8+
final class CFAbsoluteTimePrettyPrintTests: XCTestCase {
9+
10+
func testPrettyPrintForHoursAndMinutes() {
11+
12+
let interval = 2 * CFTimeInterval.hour + 15 * CFTimeInterval.minute
13+
XCTAssertEqual(interval.CC_prettyDescription, "2h 15m")
14+
}
15+
16+
func testPrettyPrintForMinutesAndSeconds() {
17+
18+
let interval = 1 * CFTimeInterval.minute + 45 * CFTimeInterval.second
19+
XCTAssertEqual(interval.CC_prettyDescription, "1m 45s")
20+
}
21+
22+
func testPrettyPrintForSecondsAndMilliseconds() {
23+
24+
let interval = 3 * CFTimeInterval.second + 400 * CFTimeInterval.ms
25+
XCTAssertEqual(interval.CC_prettyDescription, "3s 400ms")
26+
}
27+
28+
func testPrettyPrintFallsBackToNanoseconds() {
29+
30+
let interval = 250 * CFTimeInterval.ns
31+
let pretty = interval.CC_prettyDescription
32+
XCTAssertTrue(pretty.hasSuffix("ns"))
33+
34+
let numericPortion = pretty.dropLast(2)
35+
guard let value = Double(numericPortion) else {
36+
return XCTFail("Expected numeric portion in nanosecond description: \\(pretty)")
37+
}
38+
XCTAssertEqual(value, 250.0, accuracy: 0.0001)
39+
}
40+
}
Lines changed: 86 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,86 @@
1+
//
2+
// Cornucopia – (C) Dr. Lauer Information Technology
3+
//
4+
import Foundation
5+
import XCTest
6+
@testable import CornucopiaCore
7+
8+
final class StreamThrowingIOTests: XCTestCase {
9+
10+
func testInputStreamThrowingReadTransfersBytes() throws {
11+
12+
let payload = Data("cornucopia".utf8)
13+
let stream = InputStream(data: payload)
14+
stream.open()
15+
defer { stream.close() }
16+
17+
var buffer = [UInt8](repeating: 0, count: payload.count)
18+
let bytesRead = try buffer.withUnsafeMutableBufferPointer { pointer -> Int in
19+
guard let baseAddress = pointer.baseAddress else { XCTFail("Pointer base address not available."); return 0 }
20+
return try stream.CC_read(baseAddress, maxLength: pointer.count)
21+
}
22+
23+
XCTAssertEqual(bytesRead, payload.count)
24+
XCTAssertEqual(Data(buffer), payload)
25+
}
26+
27+
func testInputStreamThrowingReadThrowsEOF() throws {
28+
29+
let stream = InputStream(data: Data([0x01]))
30+
stream.open()
31+
defer { stream.close() }
32+
33+
var buffer = [UInt8](repeating: 0, count: 1)
34+
_ = try buffer.withUnsafeMutableBufferPointer { pointer -> Int in
35+
guard let baseAddress = pointer.baseAddress else { XCTFail("Pointer base address not available."); return 0 }
36+
return try stream.CC_read(baseAddress, maxLength: pointer.count)
37+
}
38+
39+
XCTAssertThrowsError(try buffer.withUnsafeMutableBufferPointer { pointer -> Int in
40+
guard let baseAddress = pointer.baseAddress else { XCTFail("Pointer base address not available."); return 0 }
41+
return try stream.CC_read(baseAddress, maxLength: pointer.count)
42+
}) { error in
43+
guard case InputStream.Exception.eof? = error as? InputStream.Exception else {
44+
return XCTFail("Expected EOF, got \\(error)")
45+
}
46+
}
47+
}
48+
49+
func testOutputStreamThrowingWritePersistsData() throws {
50+
51+
let stream = OutputStream.toMemory()
52+
stream.open()
53+
defer { stream.close() }
54+
55+
let payload: [UInt8] = [0xCA, 0xFE, 0xBA, 0xBE]
56+
let written = try payload.withUnsafeBytes { pointer -> Int in
57+
guard let baseAddress = pointer.bindMemory(to: UInt8.self).baseAddress else {
58+
XCTFail("Pointer base address not available."); return 0
59+
}
60+
return try stream.CC_write(baseAddress, maxLength: payload.count)
61+
}
62+
63+
XCTAssertEqual(written, payload.count)
64+
let data = stream.property(forKey: .dataWrittenToMemoryStreamKey) as? Data
65+
XCTAssertEqual(data, Data(payload))
66+
}
67+
68+
func testOutputStreamThrowingWriteThrowsWhenClosed() {
69+
70+
let stream = OutputStream.toMemory()
71+
stream.open()
72+
stream.close()
73+
74+
let payload: [UInt8] = [0x00]
75+
XCTAssertThrowsError(try payload.withUnsafeBytes { pointer -> Int in
76+
guard let baseAddress = pointer.bindMemory(to: UInt8.self).baseAddress else {
77+
XCTFail("Pointer base address not available."); return 0
78+
}
79+
return try stream.CC_write(baseAddress, maxLength: payload.count)
80+
}) { error in
81+
guard case OutputStream.Exception.unknown? = error as? OutputStream.Exception else {
82+
return XCTFail("Expected unknown error, got \\(error)")
83+
}
84+
}
85+
}
86+
}

0 commit comments

Comments
 (0)