-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathWebSocketTests.swift
More file actions
113 lines (96 loc) · 4.62 KB
/
WebSocketTests.swift
File metadata and controls
113 lines (96 loc) · 4.62 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
@testable import App
import XCTVapor
final class WebSocketTests: AppLiveTestCase {
override func setUp() {
super.setUp()
try! app.startServer()
}
override func tearDown() {
app.stopServer()
super.tearDown()
}
func test_01_sendingMessageOverWebSocket() async throws {
let current = try await service.seedCurrentUser()
let users = try await service.seedUsers(count: 1, namePrefix: "User", usernamePrefix: "user")
let chat = try await service.makeChat(ownerId: current.id!, users: users.map { $0.id! }, isPersonal: true)
// Login both users:
var deviceSession1: DeviceSession.Info!
var deviceSession2: DeviceSession.Info!
try app.sendRequest(.POST, "api/users/login",
headers: .authWith(username: CurrentUser.username, password: CurrentUser.password),
beforeRequest: { req in
try req.content.encode(
DeviceInfo.testInfoDesktop
)
}, afterRequest: { res in
XCTAssertEqual(res.status, .ok, res.body.string)
let privateInfo = try res.content.decode(User.PrivateInfo.self)
deviceSession1 = try XCTUnwrap(privateInfo.sessionForDeviceId(DeviceInfo.testInfoDesktop.id))
})
try app.sendRequest(.POST, "api/users/login",
headers: .authWith(username: users[0].username, password: ""),
beforeRequest: { req in
try req.content.encode(
DeviceInfo.testInfoDesktop
)
}, afterRequest: { res in
XCTAssertEqual(res.status, .ok, res.body.string)
let privateInfo = try res.content.decode(User.PrivateInfo.self)
deviceSession2 = try XCTUnwrap(privateInfo.sessionForDeviceId(DeviceInfo.testInfoDesktop.id))
})
// Subroutine to check the validity of the incoming message:
let assertMessageFromBuffer: @Sendable (ByteBuffer) -> () = { buffer in
let data = Data(buffer: buffer)
let json = try! data.json() as! JSON
let payload = json["payload"] as! JSON
// Received message! 🎉🎉🎉
let message = try! MessageInfo.fromData(payload.data())
XCTAssertEqual(message.text, "Hey")
XCTAssertEqual(message.author?.id, 1)
XCTAssertEqual(json["event"] as! String, "message")
XCTAssertEqual(UserID(json["source"] as! String), message.author?.id)
}
// Connect web sockets of both users:
let expectation1 = XCTestExpectation(description: "Ping 1")
let expectation2 = XCTestExpectation(description: "Ping 2")
let expectation3 = XCTestExpectation(description: "Message")
expectation3.expectedFulfillmentCount = 3
try await WebSocket.connect(to: "ws://localhost:8080/ws/\(deviceSession1.id)",
headers: .authWith(token: deviceSession1.accessToken),
on: app.eventLoopGroup) { ws in
ws.onPing { ws, buf in
expectation1.fulfill()
}
ws.onBinary { ws, buf in
assertMessageFromBuffer(buf)
expectation3.fulfill()
ws.close()
}
}
try await WebSocket.connect(to: "ws://localhost:8080/ws/\(deviceSession2.id)",
headers: .authWith(token: deviceSession2.accessToken),
on: app.eventLoopGroup) { ws in
ws.onPing { ws, buf in
expectation2.fulfill()
}
ws.onBinary { ws, buf in
assertMessageFromBuffer(buf)
expectation3.fulfill()
ws.close()
}
}
await fulfillment(of: [expectation1, expectation2], timeout: 10)
// Sending message from user1 to user2:
try await asyncTest(.POST, "api/chats/\(chat.id!)/messages", headers: .authWith(token: deviceSession1.accessToken), beforeRequest: { req in
try req.content.encode(
PostMessageRequest(localId: UUID().uuidString, text: "Hey")
)
}, afterResponse: { res in
XCTAssertEqual(res.status, .ok, res.body.string)
let message = try res.content.decode(MessageInfo.self)
XCTAssertEqual(message.text, "Hey")
expectation3.fulfill()
})
await fulfillment(of: [expectation3], timeout: 10)
}
}