From 1e4d7815bac3e02ef4ef1c1f16a4a183c68286b2 Mon Sep 17 00:00:00 2001 From: Honza Dvorsky Date: Wed, 17 Jul 2024 15:59:04 +0200 Subject: [PATCH 1/2] Support NSNull in OpenAPIContainer types --- Sources/OpenAPIRuntime/Base/OpenAPIValue.swift | 13 +++++++++++++ .../Base/Test_OpenAPIValue.swift | 17 +++++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift b/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift index 0d39a6c4..a8607ed2 100644 --- a/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift +++ b/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift @@ -12,6 +12,10 @@ // //===----------------------------------------------------------------------===// +#if canImport(Foundation) +import class Foundation.NSNull +#endif + /// A container for a value represented by JSON Schema. /// /// Contains an untyped JSON value. In some cases, the structure of the data @@ -62,6 +66,9 @@ public struct OpenAPIValueContainer: Codable, Hashable, Sendable { /// - Throws: When the value is not supported. static func tryCast(_ value: (any Sendable)?) throws -> (any Sendable)? { guard let value = value else { return nil } + #if canImport(Foundation) + if value is NSNull { return value } + #endif if let array = value as? [(any Sendable)?] { return try array.map(tryCast(_:)) } if let dictionary = value as? [String: (any Sendable)?] { return try dictionary.mapValues(tryCast(_:)) } if let value = tryCastPrimitiveType(value) { return value } @@ -123,6 +130,12 @@ public struct OpenAPIValueContainer: Codable, Hashable, Sendable { try container.encodeNil() return } + #if canImport(Foundation) + if value is NSNull { + try container.encodeNil() + return + } + #endif switch value { case let value as Bool: try container.encode(value) case let value as Int: try container.encode(value) diff --git a/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift b/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift index d95ee8c4..0f24a1ad 100644 --- a/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift +++ b/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift @@ -12,6 +12,9 @@ // //===----------------------------------------------------------------------===// import XCTest +#if canImport(Foundation) +import Foundation +#endif @_spi(Generated) @testable import OpenAPIRuntime final class Test_OpenAPIValue: Test_Runtime { @@ -22,6 +25,10 @@ final class Test_OpenAPIValue: Test_Runtime { _ = OpenAPIValueContainer(1) _ = OpenAPIValueContainer(4.5) + #if canImport(Foundation) + XCTAssertEqual(try OpenAPIValueContainer(unvalidatedValue: NSNull()).value as? NSNull, NSNull()) + #endif + _ = try OpenAPIValueContainer(unvalidatedValue: ["hello"]) _ = try OpenAPIValueContainer(unvalidatedValue: ["hello": "world"]) @@ -60,6 +67,16 @@ final class Test_OpenAPIValue: Test_Runtime { """# try _testPrettyEncoded(container, expectedJSON: expectedString) } + #if canImport(Foundation) + func testEncodingNSNull() throws { + let value = NSNull() + let container = try OpenAPIValueContainer(unvalidatedValue: value) + let expectedString = #""" + null + """# + try _testPrettyEncoded(container, expectedJSON: expectedString) + } + #endif func testEncoding_container_failure() throws { struct Foobar: Equatable {} From aab45bb749dd1f3795769048150eab579773a345 Mon Sep 17 00:00:00 2001 From: Honza Dvorsky Date: Wed, 17 Jul 2024 16:22:51 +0200 Subject: [PATCH 2/2] Handle preconcurrency foundations --- Sources/OpenAPIRuntime/Base/OpenAPIValue.swift | 4 ++++ Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift | 6 +++++- 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift b/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift index a8607ed2..2bb98f4c 100644 --- a/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift +++ b/Sources/OpenAPIRuntime/Base/OpenAPIValue.swift @@ -13,7 +13,11 @@ //===----------------------------------------------------------------------===// #if canImport(Foundation) +#if canImport(Darwin) import class Foundation.NSNull +#else +@preconcurrency import class Foundation.NSNull +#endif #endif /// A container for a value represented by JSON Schema. diff --git a/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift b/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift index 0f24a1ad..89a4a5a8 100644 --- a/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift +++ b/Tests/OpenAPIRuntimeTests/Base/Test_OpenAPIValue.swift @@ -13,7 +13,11 @@ //===----------------------------------------------------------------------===// import XCTest #if canImport(Foundation) -import Foundation +#if canImport(Darwin) +import class Foundation.NSNull +#else +@preconcurrency import class Foundation.NSNull +#endif #endif @_spi(Generated) @testable import OpenAPIRuntime