1
0
Fork 0
mirror of https://github.com/denoland/deno.git synced 2024-12-25 08:39:09 -05:00

perf(ext/websocket): various performance improvements (#18862)

- No need to wrap buffer in a `new DataView()`
- Deferred ops are still eagerly polled, but resolved on the next
tick of the event loop, we don't want them to be eagerly polled
- Using "core.opAsync"/"core.opAsync2" incurs additional cost
of looking up these functions on each call. Similarly with "ops.*"

---------

Co-authored-by: Divy Srivastava <dj.srivastava23@gmail.com>
This commit is contained in:
Bartek Iwańczuk 2023-04-27 12:47:52 +02:00 committed by GitHub
parent 1e331a4873
commit d043a6d72c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 16 additions and 16 deletions

View file

@ -3,7 +3,10 @@
/// <reference path="../../core/internal.d.ts" /> /// <reference path="../../core/internal.d.ts" />
const core = globalThis.Deno.core; const core = globalThis.Deno.core;
const ops = core.ops; const { opAsync, opAsync2 } = core;
// deno-lint-ignore camelcase
const op_ws_check_permission_and_cancel_handle =
core.ops.op_ws_check_permission_and_cancel_handle;
import { URL } from "ext:deno_url/00_url.js"; import { URL } from "ext:deno_url/00_url.js";
import * as webidl from "ext:deno_webidl/00_webidl.js"; import * as webidl from "ext:deno_webidl/00_webidl.js";
import { HTTP_TOKEN_CODE_POINT_RE } from "ext:deno_web/00_infra.js"; import { HTTP_TOKEN_CODE_POINT_RE } from "ext:deno_web/00_infra.js";
@ -210,7 +213,7 @@ class WebSocket extends EventTarget {
this[_url] = wsURL.href; this[_url] = wsURL.href;
this[_role] = CLIENT; this[_role] = CLIENT;
ops.op_ws_check_permission_and_cancel_handle( op_ws_check_permission_and_cancel_handle(
"WebSocket.abort()", "WebSocket.abort()",
this[_url], this[_url],
false, false,
@ -247,7 +250,7 @@ class WebSocket extends EventTarget {
} }
PromisePrototypeThen( PromisePrototypeThen(
core.opAsync( opAsync(
"op_ws_create", "op_ws_create",
"new WebSocket()", "new WebSocket()",
wsURL.href, wsURL.href,
@ -260,7 +263,7 @@ class WebSocket extends EventTarget {
if (this[_readyState] === CLOSING) { if (this[_readyState] === CLOSING) {
PromisePrototypeThen( PromisePrototypeThen(
core.opAsync("op_ws_close", this[_rid]), opAsync("op_ws_close", this[_rid]),
() => { () => {
this[_readyState] = CLOSED; this[_readyState] = CLOSED;
@ -316,7 +319,7 @@ class WebSocket extends EventTarget {
const sendTypedArray = (view, byteLength) => { const sendTypedArray = (view, byteLength) => {
this[_bufferedAmount] += byteLength; this[_bufferedAmount] += byteLength;
PromisePrototypeThen( PromisePrototypeThen(
core.opAsync2( opAsync2(
"op_ws_send_binary", "op_ws_send_binary",
this[_rid], this[_rid],
view, view,
@ -345,16 +348,13 @@ class WebSocket extends EventTarget {
sendTypedArray(data, TypedArrayPrototypeGetByteLength(data)); sendTypedArray(data, TypedArrayPrototypeGetByteLength(data));
} }
} else if (ObjectPrototypeIsPrototypeOf(ArrayBufferPrototype, data)) { } else if (ObjectPrototypeIsPrototypeOf(ArrayBufferPrototype, data)) {
sendTypedArray( sendTypedArray(data, ArrayBufferPrototypeGetByteLength(data));
new DataView(data),
ArrayBufferPrototypeGetByteLength(data),
);
} else { } else {
const string = String(data); const string = String(data);
const d = core.encode(string); const d = core.encode(string);
this[_bufferedAmount] += TypedArrayPrototypeGetByteLength(d); this[_bufferedAmount] += TypedArrayPrototypeGetByteLength(d);
PromisePrototypeThen( PromisePrototypeThen(
core.opAsync2( opAsync2(
"op_ws_send_text", "op_ws_send_text",
this[_rid], this[_rid],
string, string,
@ -413,7 +413,7 @@ class WebSocket extends EventTarget {
this[_readyState] = CLOSING; this[_readyState] = CLOSING;
PromisePrototypeCatch( PromisePrototypeCatch(
core.opAsync( opAsync(
"op_ws_close", "op_ws_close",
this[_rid], this[_rid],
code, code,
@ -438,7 +438,7 @@ class WebSocket extends EventTarget {
async [_eventLoop]() { async [_eventLoop]() {
while (this[_readyState] !== CLOSED) { while (this[_readyState] !== CLOSED) {
const { 0: kind, 1: value } = await core.opAsync2( const { 0: kind, 1: value } = await opAsync2(
"op_ws_next_event", "op_ws_next_event",
this[_rid], this[_rid],
); );
@ -501,7 +501,7 @@ class WebSocket extends EventTarget {
if (prevState === OPEN) { if (prevState === OPEN) {
try { try {
await core.opAsync( await opAsync(
"op_ws_close", "op_ws_close",
this[_rid], this[_rid],
code, code,
@ -530,12 +530,12 @@ class WebSocket extends EventTarget {
clearTimeout(this[_idleTimeoutTimeout]); clearTimeout(this[_idleTimeoutTimeout]);
this[_idleTimeoutTimeout] = setTimeout(async () => { this[_idleTimeoutTimeout] = setTimeout(async () => {
if (this[_readyState] === OPEN) { if (this[_readyState] === OPEN) {
await core.opAsync("op_ws_send_ping", this[_rid]); await opAsync("op_ws_send_ping", this[_rid]);
this[_idleTimeoutTimeout] = setTimeout(async () => { this[_idleTimeoutTimeout] = setTimeout(async () => {
if (this[_readyState] === OPEN) { if (this[_readyState] === OPEN) {
this[_readyState] = CLOSING; this[_readyState] = CLOSING;
const reason = "No response from ping frame."; const reason = "No response from ping frame.";
await core.opAsync( await opAsync(
"op_ws_close", "op_ws_close",
this[_rid], this[_rid],
1001, 1001,

View file

@ -427,7 +427,7 @@ pub async fn op_ws_close(
Ok(()) Ok(())
} }
#[op(deferred)] #[op(fast)]
pub async fn op_ws_next_event( pub async fn op_ws_next_event(
state: Rc<RefCell<OpState>>, state: Rc<RefCell<OpState>>,
rid: ResourceId, rid: ResourceId,