diff options
author | Bartek IwaĆczuk <biwanczuk@gmail.com> | 2020-03-19 00:25:55 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-03-18 19:25:55 -0400 |
commit | 6e2df8c64feb92653077a5494d2c64a9f6fd2f48 (patch) | |
tree | d359310f24622ef38b57538fcdc698f6cadb620d /std/ws/test.ts | |
parent | 070464e2cc617ecbd2c63dc5c4ac0432a77a29fd (diff) |
feat: Deno.test() sanitizes ops and resources (#4399)
This PR brings assertOps and assertResources sanitizers to Deno.test() API.
assertOps checks that test doesn't leak async ops, ie. there are no unresolved
promises originating from Deno APIs. Enabled by default, can be disabled using
Deno.TestDefinition.disableOpSanitizer.
assertResources checks that test doesn't leak resources, ie. all resources used
in test are closed. For example; if a file is opened during a test case it must be
explicitly closed before test case finishes. It's most useful for asynchronous
generators. Enabled by default, can be disabled using
Deno.TestDefinition.disableResourceSanitizer.
We've used those sanitizers in internal runtime tests and it proved very useful in
surfacing incorrect tests which resulted in interference between the tests.
All tests have been sanitized.
Closes #4208
Diffstat (limited to 'std/ws/test.ts')
-rw-r--r-- | std/ws/test.ts | 109 |
1 files changed, 59 insertions, 50 deletions
diff --git a/std/ws/test.ts b/std/ws/test.ts index e0050bcf4..820fe1423 100644 --- a/std/ws/test.ts +++ b/std/ws/test.ts @@ -21,6 +21,7 @@ import Writer = Deno.Writer; import Reader = Deno.Reader; import Conn = Deno.Conn; import Buffer = Deno.Buffer; +import { delay } from "../util/async.ts"; test("[ws] read unmasked text frame", async () => { // unmasked single text frame with payload "Hello" @@ -296,31 +297,32 @@ function delayedWriter(ms: number, dest: Writer): Writer { } }; } -test("[ws] WebSocket.send(), WebSocket.ping() should be exclusive", async (): Promise< - void -> => { - const buf = new Buffer(); - const conn = dummyConn(new Buffer(), delayedWriter(1, buf)); - const sock = createWebSocket({ conn }); - // Ensure send call - await Promise.all([ - sock.send("first"), - sock.send("second"), - sock.ping(), - sock.send(new Uint8Array([3])) - ]); - const bufr = new BufReader(buf); - const first = await readFrame(bufr); - const second = await readFrame(bufr); - const ping = await readFrame(bufr); - const third = await readFrame(bufr); - assertEquals(first.opcode, OpCode.TextFrame); - assertEquals(decode(first.payload), "first"); - assertEquals(first.opcode, OpCode.TextFrame); - assertEquals(decode(second.payload), "second"); - assertEquals(ping.opcode, OpCode.Ping); - assertEquals(third.opcode, OpCode.BinaryFrame); - assertEquals(bytes.equal(third.payload, new Uint8Array([3])), true); +test({ + name: "[ws] WebSocket.send(), WebSocket.ping() should be exclusive", + fn: async (): Promise<void> => { + const buf = new Buffer(); + const conn = dummyConn(new Buffer(), delayedWriter(1, buf)); + const sock = createWebSocket({ conn }); + // Ensure send call + await Promise.all([ + sock.send("first"), + sock.send("second"), + sock.ping(), + sock.send(new Uint8Array([3])) + ]); + const bufr = new BufReader(buf); + const first = await readFrame(bufr); + const second = await readFrame(bufr); + const ping = await readFrame(bufr); + const third = await readFrame(bufr); + assertEquals(first.opcode, OpCode.TextFrame); + assertEquals(decode(first.payload), "first"); + assertEquals(first.opcode, OpCode.TextFrame); + assertEquals(decode(second.payload), "second"); + assertEquals(ping.opcode, OpCode.Ping); + assertEquals(third.opcode, OpCode.BinaryFrame); + assertEquals(bytes.equal(third.payload, new Uint8Array([3])), true); + } }); test("[ws] createSecKeyHasCorrectLength", () => { @@ -363,29 +365,36 @@ test("[ws] WebSocket shouldn't throw `Deno.errors.UnexpectedEof` on recive()", a assertEquals(done, true); }); -test("[ws] WebSocket should reject sending promise when connection reset forcely", async () => { - const buf = new Buffer(); - let timer: number | undefined; - const lazyWriter: Deno.Writer = { - async write(_: Uint8Array): Promise<number> { - return new Promise(resolve => { - timer = setTimeout(() => resolve(0), 1000); - }); - } - }; - const conn = dummyConn(buf, lazyWriter); - const sock = createWebSocket({ conn }); - const onError = (e: unknown): unknown => e; - const p = Promise.all([ - sock.send("hello").catch(onError), - sock.send(new Uint8Array([1, 2])).catch(onError), - sock.ping().catch(onError) - ]); - sock.closeForce(); - assertEquals(sock.isClosed, true); - const [a, b, c] = await p; - assert(a instanceof Deno.errors.ConnectionReset); - assert(b instanceof Deno.errors.ConnectionReset); - assert(c instanceof Deno.errors.ConnectionReset); - clearTimeout(timer); +test({ + name: + "[ws] WebSocket should reject sending promise when connection reset forcely", + fn: async () => { + const buf = new Buffer(); + let timer: number | undefined; + const lazyWriter: Deno.Writer = { + async write(_: Uint8Array): Promise<number> { + return new Promise(resolve => { + timer = setTimeout(() => resolve(0), 1000); + }); + } + }; + const conn = dummyConn(buf, lazyWriter); + const sock = createWebSocket({ conn }); + const onError = (e: unknown): unknown => e; + const p = Promise.all([ + sock.send("hello").catch(onError), + sock.send(new Uint8Array([1, 2])).catch(onError), + sock.ping().catch(onError) + ]); + sock.closeForce(); + assertEquals(sock.isClosed, true); + const [a, b, c] = await p; + assert(a instanceof Deno.errors.ConnectionReset); + assert(b instanceof Deno.errors.ConnectionReset); + assert(c instanceof Deno.errors.ConnectionReset); + clearTimeout(timer); + // Wait for another event loop turn for `timeout` op promise + // to resolve, otherwise we'll get "op leak". + await delay(10); + } }); |