Skip to content

Commit

Permalink
more datagram tests
Browse files Browse the repository at this point in the history
  • Loading branch information
swhitty committed Nov 23, 2024
1 parent 9aeebe9 commit 25c704e
Show file tree
Hide file tree
Showing 2 changed files with 78 additions and 38 deletions.
4 changes: 2 additions & 2 deletions FlyingSocks/Sources/AsyncSocket.swift
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,7 @@ public struct AsyncSocket: Sendable {
repeat {
do {
let (peerAddress, bytes, interfaceIndex, localAddress) = try socket.receive(length: length)
return Message(peerAddress: peerAddress, bytes: bytes, interfaceIndex: interfaceIndex, localAddress: localAddress)
return Message(peerAddress: peerAddress, payload: Data(bytes), interfaceIndex: interfaceIndex, localAddress: localAddress)
} catch SocketError.blocked {
try await pool.suspendSocket(socket, untilReadyFor: .read)
} catch {
Expand Down Expand Up @@ -264,7 +264,7 @@ public struct AsyncSocket: Sendable {

public func send(message: Message) async throws {
try await send(
message: message.bytes,
message: message.payload,
to: AnySocketAddress(message.peerAddress),
interfaceIndex: message.interfaceIndex,
from: message.localAddress
Expand Down
112 changes: 76 additions & 36 deletions FlyingSocks/Tests/AsyncSocketTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -209,52 +209,43 @@ struct AsyncSocketTests {
}

#if !canImport(WinSDK)
#if canImport(Darwin)
@Test
func datagramSocketReceivesMessageTupleAPI_WhenAvailable() async throws {
let (s1, s2, addr) = try await AsyncSocket.makeDatagramPair()
func messageSequence_sendsMessage_receivesTuple() async throws {
let (socket, port) = try await AsyncSocket.makeLoopbackDatagram()

async let d2: AsyncSocket.Message = s2.receive(atMost: 100)
#if canImport(Darwin)
try await s1.write("Swift".data(using: .utf8)!)
#else
try await s1.send(message: "Swift".data(using: .utf8)!, to: addr, from: addr)
#endif
let v2 = try await d2
#expect(String(data: Data(v2.bytes), encoding: .utf8) == "Swift")
async let received: (any SocketAddress, [UInt8]) = socket.receive(atMost: 100)

try s1.close()
try s2.close()
try? Socket.unlink(addr)
}
#endif
let client = try await AsyncSocket.makeLoopbackDatagram().0
let message = AsyncSocket.Message(peerAddress: .loopback(port: port), payload: "Chips 🍟")
try await client.send(message: message)

#if !canImport(WinSDK)
#expect(
try await received.1 == Array("Chips 🍟".data(using: .utf8)!)
)
}
#else
@Test
func datagramSocketReceivesMessageStructAPI_WhenAvailable() async throws {
func messageSequence_sendsMessage_receivesTuple() async throws {
let (s1, s2, addr) = try await AsyncSocket.makeDatagramPair()
let messageToSend = AsyncSocket.Message(
peerAddress: addr,
bytes: Array("Swift".data(using: .utf8)!),
localAddress: addr
)
defer {
try? s1.close()
try? s2.close()
try? Socket.unlink(addr)
}
async let received: (any SocketAddress, [UInt8]) = s2.receive(atMost: 100)

async let d2: AsyncSocket.Message = s2.receive(atMost: 100)
#if canImport(Darwin)
try await s1.write("Swift".data(using: .utf8)!)
#else
try await s1.send(message: messageToSend)
#endif
let v2 = try await d2
#expect(String(data: Data(v2.bytes), encoding: .utf8) == "Swift")
let message = AsyncSocket.Message(peerAddress: addr, payload: "Shrimp 🦐")
try await s1.send(message: message)

try s1.close()
try s2.close()
try? Socket.unlink(addr)
#expect(
try await received.1 == Array("Shrimp 🦐".data(using: .utf8)!)
)
}
#endif
#endif

@Test
func messageSequence_receives_messages() async throws {
func messageSequence_sendsData_receivesMessage() async throws {
let (socket, port) = try await AsyncSocket.makeLoopbackDatagram()
var messages = socket.messages

Expand All @@ -267,6 +258,48 @@ struct AsyncSocketTests {
try await received?.payloadString == "Fish 🐡"
)
}

#if canImport(Darwin)
@Test
func messageSequence_sendsMessage_receivesMessage() async throws {
let (socket, port) = try await AsyncSocket.makeLoopbackDatagram()
var messages = socket.messages

async let received = messages.next()

let client = try await AsyncSocket.makeLoopbackDatagram().0
let message = AsyncSocket.Message(peerAddress: .loopback(port: port), payload: "Chips 🍟")
try await client.send(message: message)

#expect(
try await received?.payloadString == "Chips 🍟"
)
}
#else
@Test
func messageSequence_sendsMessage_receivesMessage() async throws {
let (s1, s2, addr) = try await AsyncSocket.makeDatagramPair()
defer {
try? s1.close()
try? s2.close()
try? Socket.unlink(addr)
}
var messages = socket.messages

async let received = s2.next()

let message = AsyncSocket.Message(peerAddress: addr, payload: "Shrimp 🦐")
try await client.send(message: message)

async let d2: AsyncSocket.Message = s2.receive(atMost: 100)
try await s1.send(message: messageToSend)

#expect(
try await received?.payloadString == "Shrimp 🦐"
)
}
#endif
#endif
}

extension AsyncSocket {
Expand Down Expand Up @@ -341,12 +374,19 @@ private extension AsyncSocket.Message {

var payloadString: String {
get throws {
guard let text = String(bytes: bytes, encoding: .utf8) else {
guard let text = String(data: payload, encoding: .utf8) else {
throw SocketError.disconnected
}
return text
}
}

init(peerAddress: some SocketAddress, payload: String) {
self.init(
peerAddress: peerAddress,
payload: payload.data(using: .utf8)!
)
}
}

struct DisconnectedPool: AsyncSocketPool {
Expand Down

0 comments on commit 25c704e

Please sign in to comment.