diff --git a/Sources/Testing/Attachments/Attachment.swift b/Sources/Testing/Attachments/Attachment.swift index b665b99fe..932a1bcf7 100644 --- a/Sources/Testing/Attachments/Attachment.swift +++ b/Sources/Testing/Attachments/Attachment.swift @@ -97,6 +97,19 @@ public struct Attachment where AttachableValue: Attachable & ~C extension Attachment: Sendable where AttachableValue: Sendable {} extension Attachment.Storage: Sendable where AttachableValue: Sendable {} +#if !hasFeature(Embedded) +/// A protocol that describes an attachment with a copyable value. +/// +/// We can use this protocol to make runtime decisions about attachments based +/// on whether or not their attachable values are copyable. +private protocol _AttachmentWithCopyableValue { + associatedtype AttachableValue: Attachable & Copyable + var attachableValue: AttachableValue { get } +} + +extension Attachment: _AttachmentWithCopyableValue where AttachableValue: Copyable {} +#endif + // MARK: - Initializing an attachment extension Attachment where AttachableValue: ~Copyable { @@ -180,21 +193,19 @@ public struct AnyAttachable: AttachableWrapper, Sendable, Copyable { // MARK: - Describing an attachment -extension Attachment where AttachableValue: ~Copyable { - @_documentation(visibility: private) - public var description: String { - let typeInfo = TypeInfo(describing: AttachableValue.self) - return #""\#(preferredName)": instance of '\#(typeInfo.unqualifiedName)'"# - } -} - -extension Attachment: CustomStringConvertible { +extension Attachment: CustomStringConvertible where AttachableValue: ~Copyable { /// @Metadata { /// @Available(Swift, introduced: 6.2) /// @Available(Xcode, introduced: 26.0) /// } public var description: String { - #""\#(preferredName)": \#(String(describingForTest: attachableValue))"# +#if !hasFeature(Embedded) + if let selfCopy = self as? any _AttachmentWithCopyableValue { + return #""\#(preferredName)": \#(String(describingForTest: selfCopy.attachableValue))"# + } +#endif + let typeInfo = TypeInfo(describing: AttachableValue.self) + return #""\#(preferredName)": instance of '\#(typeInfo.unqualifiedName)'"# } } diff --git a/Tests/TestingTests/AttachmentTests.swift b/Tests/TestingTests/AttachmentTests.swift index 7695dd634..2b8d3e840 100644 --- a/Tests/TestingTests/AttachmentTests.swift +++ b/Tests/TestingTests/AttachmentTests.swift @@ -50,15 +50,15 @@ struct AttachmentTests { let attachableValue = MySendableAttachable(string: "") let attachment = Attachment(attachableValue, named: "AttachmentTests.saveValue.html") #expect(String(describing: attachment).contains(#""\#(attachment.preferredName)""#)) - #expect(attachment.description.contains("MySendableAttachable(")) + #expect(String(describing: attachment).contains("MySendableAttachable(")) } #if compiler(>=6.3) || !os(Windows) // WORKAROUND: swift-#84184 @Test func moveOnlyDescription() { let attachableValue = MyAttachable(string: "") let attachment = Attachment(attachableValue, named: "AttachmentTests.saveValue.html") - #expect(attachment.description.contains(#""\#(attachment.preferredName)""#)) - #expect(attachment.description.contains("'MyAttachable'")) + #expect(String(describing: attachment).contains(#""\#(attachment.preferredName)""#)) + #expect(String(describing: attachment).contains("'MyAttachable'")) } #endif