Skip to content

Commit 66eafc8

Browse files
Improve test reliability.
1 parent c330de6 commit 66eafc8

File tree

3 files changed

+93
-135
lines changed

3 files changed

+93
-135
lines changed

test/unit/helpers.ts

Lines changed: 23 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,8 @@ export function uniqAddress(proto: string) {
1616
const id = seq++
1717
switch (proto) {
1818
case "ipc":
19-
return `${proto}://${__dirname}/../../tmp/${proto}-${id}`
19+
const sock = path.resolve(__dirname, `../../tmp/${proto}-${id}`)
20+
return `${proto}://${sock}`
2021
case "tcp":
2122
case "udp":
2223
return `${proto}://127.0.0.1:${id}`
@@ -103,3 +104,24 @@ export function createProcess(fn: () => void): Promise<number> {
103104
}, 750)
104105
})
105106
}
107+
108+
export function captureEvent<E extends zmq.EventType>(
109+
socket: zmq.Socket,
110+
type: E,
111+
): Promise<zmq.EventOfType<E>> {
112+
return new Promise((resolve) => socket.events.on<E>(type, resolve))
113+
}
114+
115+
export async function captureEventsUntil(
116+
socket: zmq.Socket,
117+
type: zmq.EventType,
118+
): Promise<zmq.Event[]> {
119+
const events = []
120+
121+
for await (const event of socket.events) {
122+
events.push(event)
123+
if (event.type === type) break
124+
}
125+
126+
return events
127+
}

test/unit/socket-events-test.ts

Lines changed: 52 additions & 115 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import * as zmq from "../../src"
22

33
import {assert} from "chai"
4-
import {testProtos, uniqAddress} from "./helpers"
4+
import {captureEvent, captureEventsUntil, testProtos, uniqAddress} from "./helpers"
55

66
for (const proto of testProtos("tcp", "ipc", "inproc")) {
77
describe(`socket with ${proto} events`, function() {
@@ -21,18 +21,10 @@ for (const proto of testProtos("tcp", "ipc", "inproc")) {
2121

2222
describe("when not connected", function() {
2323
it("should receive events", async function() {
24-
const events: zmq.Event[] = []
25-
26-
const read = async () => {
27-
for await (const event of sockA.events) {
28-
events.push(event)
29-
}
30-
}
31-
32-
const done = read()
33-
await sockA.close()
34-
await done
24+
const done = captureEventsUntil(sockA, "end")
25+
sockA.close()
3526

27+
const events = await done
3628
assert.deepEqual(events, [{type: "end"}])
3729
})
3830
})
@@ -42,110 +34,50 @@ for (const proto of testProtos("tcp", "ipc", "inproc")) {
4234
assert.equal(sockA.events, sockA.events)
4335
})
4436

45-
it("should receive bind events", async function() {
46-
const address = uniqAddress(proto)
47-
const events: zmq.Event[] = []
48-
49-
const read = async () => {
50-
for await (const event of sockA.events) {
51-
events.push(event)
52-
}
53-
}
54-
55-
const done = read()
37+
if (proto !== "inproc") {
38+
it("should receive bind events", async function() {
39+
const address = uniqAddress(proto)
5640

57-
await sockA.bind(address)
58-
await sockB.connect(address)
59-
await new Promise((resolve) => setTimeout(resolve, 15))
60-
sockA.close()
61-
sockB.close()
62-
await done
63-
await new Promise((resolve) => setTimeout(resolve, 15))
41+
const [event] = await Promise.all([
42+
captureEvent(sockA, "bind"),
43+
sockA.bind(address),
44+
sockB.connect(address),
45+
])
6446

65-
if (proto === "inproc") {
66-
assert.deepEqual(events, [{type: "end"}])
67-
} else {
68-
assert.deepInclude(events, {type: "bind", address})
69-
assert.deepInclude(events, {type: "accept", address})
70-
assert.deepInclude(events, {type: "close", address})
71-
assert.deepInclude(events, {type: "end"})
72-
}
73-
})
74-
75-
it("should receive connect events", async function() {
76-
const address = uniqAddress(proto)
77-
const events: zmq.Event[] = []
78-
79-
const read = async () => {
80-
for await (const event of sockB.events) {
81-
events.push(event)
82-
}
83-
}
84-
85-
const done = read()
86-
87-
await sockA.bind(address)
88-
await sockB.connect(address)
89-
await new Promise((resolve) => setTimeout(resolve, 15))
90-
sockA.close()
91-
sockB.close()
92-
await done
93-
await new Promise((resolve) => setTimeout(resolve, 15))
94-
95-
if (proto === "inproc") {
96-
assert.deepEqual(events, [{type: "end"}])
97-
} else {
98-
if (proto === "tcp") {
99-
assert.deepInclude(events, {type: "connect:delay", address})
100-
}
101-
102-
assert.deepInclude(events, {type: "connect", address})
103-
assert.deepInclude(events, {type: "end"})
104-
}
105-
})
106-
107-
it("should receive error events", async function() {
108-
const address = uniqAddress(proto)
109-
const events: zmq.Event[] = []
110-
111-
const read = async () => {
112-
for await (const event of sockB.events) {
113-
events.push(event)
114-
}
115-
}
116-
117-
const done = read()
47+
assert.deepEqual(event, {type: "bind", address})
48+
})
11849

119-
await sockA.bind(address)
120-
try {
121-
await sockB.bind(address)
122-
} catch (err) {
123-
/* Ignore error here */
124-
}
50+
it("should receive connect events", async function() {
51+
this.slow(250)
52+
const address = uniqAddress(proto)
12553

126-
await new Promise((resolve) => setTimeout(resolve, 15))
127-
sockA.close()
128-
sockB.close()
129-
await done
54+
const [event] = await Promise.all([
55+
captureEvent(sockB, "connect"),
56+
sockA.bind(address),
57+
sockB.connect(address),
58+
])
13059

131-
if (proto === "tcp") {
132-
let bindError = false
133-
for (const event of events) {
134-
if (event.type === "bind:error") {
135-
bindError = true
136-
assert.equal("tcp://" + event.address, address)
137-
assert.instanceOf(event.error, Error)
138-
assert.equal(event.error.message, "Address already in use")
139-
assert.equal(event.error.code, "EADDRINUSE")
140-
assert.typeOf(event.error.errno, "number")
141-
}
142-
}
143-
144-
assert.equal(true, bindError)
145-
}
146-
147-
assert.deepInclude(events, {type: "end"})
148-
})
60+
assert.deepEqual(event, {type: "connect", address})
61+
})
62+
}
63+
64+
if (proto === "tcp") {
65+
it("should receive error events", async function() {
66+
const address = uniqAddress(proto)
67+
68+
await sockA.bind(address)
69+
const [event] = await Promise.all([
70+
captureEvent(sockB, "bind:error"),
71+
sockB.bind(address).catch(() => {/* Ignore */}),
72+
])
73+
74+
assert.equal("tcp://" + event.address, address)
75+
assert.instanceOf(event.error, Error)
76+
assert.equal(event.error.message, "Address already in use")
77+
assert.equal(event.error.code, "EADDRINUSE")
78+
assert.typeOf(event.error.errno, "number")
79+
})
80+
}
14981

15082
it("should receive events with emitter", async function() {
15183
const address = uniqAddress(proto)
@@ -174,13 +106,18 @@ for (const proto of testProtos("tcp", "ipc", "inproc")) {
174106
"is not possible to read events with events.receive().",
175107
)
176108

177-
await sockA.bind(address)
178-
await sockB.connect(address)
179-
await new Promise((resolve) => setTimeout(resolve, 15))
109+
const connected = captureEvent(sockB, "connect")
110+
const done = Promise.all([
111+
captureEvent(sockA, "end"),
112+
sockA.bind(address),
113+
sockB.connect(address),
114+
])
115+
116+
if (proto !== "inproc") await connected
180117
sockA.close()
181118
sockB.close()
182-
await new Promise((resolve) => setTimeout(resolve, 15))
183119

120+
await done
184121
if (proto === "inproc") {
185122
assert.deepEqual(events, [{type: "end"}])
186123
} else {

test/unit/socket-zap-test.ts

Lines changed: 18 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import * as semver from "semver"
22
import * as zmq from "../../src"
33

44
import {assert} from "chai"
5-
import {testProtos, uniqAddress} from "./helpers"
5+
import {captureEvent, testProtos, uniqAddress} from "./helpers"
66

77
for (const proto of testProtos("tcp", "ipc")) {
88
describe(`socket with ${proto} zap`, function() {
@@ -66,12 +66,12 @@ for (const proto of testProtos("tcp", "ipc")) {
6666
sockB.plainPassword = "BAD PASS"
6767

6868
const address = uniqAddress(proto)
69-
await sockA.bind(address)
70-
await sockB.connect(address)
7169

7270
const [eventA, eventB] = await Promise.all([
7371
captureEvent(sockA, "handshake:error:auth"),
7472
captureEvent(sockB, "handshake:error:auth"),
73+
sockA.bind(address),
74+
sockB.connect(address),
7575
])
7676

7777
assert.equal(eventA.type, "handshake:error:auth")
@@ -106,10 +106,12 @@ for (const proto of testProtos("tcp", "ipc")) {
106106
sockB.plainUsername = "user"
107107

108108
const address = uniqAddress(proto)
109-
await sockA.bind(address)
110-
await sockB.connect(address)
109+
const [eventA] = await Promise.all([
110+
captureEvent(sockA, "handshake:error:protocol"),
111+
sockA.bind(address),
112+
sockB.connect(address),
113+
])
111114

112-
const eventA = await captureEvent(sockA, "handshake:error:protocol")
113115
assert.equal(eventA.type, "handshake:error:protocol")
114116
assert.equal(eventA.address, address)
115117
assert.instanceOf(eventA.error, Error)
@@ -133,10 +135,12 @@ for (const proto of testProtos("tcp", "ipc")) {
133135
sockB.plainUsername = "user"
134136

135137
const address = uniqAddress(proto)
136-
await sockA.bind(address)
137-
await sockB.connect(address)
138+
const [eventA] = await Promise.all([
139+
captureEvent(sockA, "handshake:error:protocol"),
140+
sockA.bind(address),
141+
sockB.connect(address),
142+
])
138143

139-
const eventA = await captureEvent(sockA, "handshake:error:protocol")
140144
assert.equal(eventA.type, "handshake:error:protocol")
141145
assert.equal(eventA.address, address)
142146
assert.instanceOf(eventA.error, Error)
@@ -152,10 +156,12 @@ for (const proto of testProtos("tcp", "ipc")) {
152156
sockB.curveServer = true
153157

154158
const address = uniqAddress(proto)
155-
await sockA.bind(address)
156-
await sockB.connect(address)
159+
const [eventA] = await Promise.all([
160+
captureEvent(sockA, "handshake:error:protocol"),
161+
sockA.bind(address),
162+
sockB.connect(address),
163+
])
157164

158-
const eventA = await captureEvent(sockA, "handshake:error:protocol")
159165
assert.equal(eventA.type, "handshake:error:protocol")
160166
assert.equal(eventA.address, address)
161167
assert.instanceOf(eventA.error, Error)
@@ -252,10 +258,3 @@ class CustomZapHandler extends ZapHandler {
252258
this.run()
253259
}
254260
}
255-
256-
function captureEvent<E extends zmq.EventType>(
257-
socket: zmq.Socket,
258-
event: E,
259-
): Promise<zmq.EventOfType<E>> {
260-
return new Promise((resolve) => socket.events.on<E>(event, resolve))
261-
}

0 commit comments

Comments
 (0)