You've already forked node-redis
mirror of
https://github.com/redis/node-redis.git
synced 2025-08-16 08:41:57 +03:00
use socket.setNoDelay and queueMicrotask to improve latency
This commit is contained in:
@@ -444,20 +444,29 @@ export default class RedisClient<M extends RedisModules = RedisModules, S extend
|
||||
return this.#socket.disconnect();
|
||||
}
|
||||
|
||||
#isTickQueued = false;
|
||||
|
||||
#tick(): void {
|
||||
const {chunkRecommendedSize} = this.#socket;
|
||||
if (!chunkRecommendedSize) {
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: batch using process.nextTick? maybe socket.setNoDelay(false)?
|
||||
if (!this.#isTickQueued && this.#queue.waitingToBeSentCommandsLength < chunkRecommendedSize) {
|
||||
queueMicrotask(() => this.#tick());
|
||||
this.#isTickQueued = true;
|
||||
return;
|
||||
}
|
||||
|
||||
const isBuffering = this.#queue.executeChunk(chunkRecommendedSize);
|
||||
if (isBuffering === true) {
|
||||
this.#socket.once('drain', () => this.#tick());
|
||||
} else if (isBuffering === false) {
|
||||
this.#tick();
|
||||
return;
|
||||
}
|
||||
|
||||
this.#isTickQueued = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -74,6 +74,12 @@ export default class RedisCommandsQueue {
|
||||
|
||||
readonly #waitingToBeSent = new LinkedList<CommandWaitingToBeSent>();
|
||||
|
||||
#waitingToBeSentCommandsLength = 0;
|
||||
|
||||
get waitingToBeSentCommandsLength() {
|
||||
return this.#waitingToBeSentCommandsLength;
|
||||
}
|
||||
|
||||
readonly #waitingForReply = new LinkedList<CommandWaitingForReply>();
|
||||
|
||||
readonly #pubSubState = {
|
||||
@@ -97,7 +103,7 @@ export default class RedisCommandsQueue {
|
||||
reply[2],
|
||||
reply[1]
|
||||
);
|
||||
|
||||
|
||||
case 'pmessage':
|
||||
return RedisCommandsQueue.#emitPubSubMessage(
|
||||
this.#pubSubListeners.patterns.get(reply[1])!,
|
||||
@@ -108,7 +114,7 @@ export default class RedisCommandsQueue {
|
||||
case 'subscribe':
|
||||
case 'psubscribe':
|
||||
if (--this.#waitingForReply.head!.value.channelsCounter! === 0) {
|
||||
this.#shiftWaitingForReply().resolve();
|
||||
this.#shiftWaitingForReply().resolve();
|
||||
}
|
||||
return;
|
||||
}
|
||||
@@ -185,6 +191,8 @@ export default class RedisCommandsQueue {
|
||||
} else {
|
||||
this.#waitingToBeSent.pushNode(node);
|
||||
}
|
||||
|
||||
this.#waitingToBeSentCommandsLength += encodedCommand.length;
|
||||
});
|
||||
}
|
||||
|
||||
@@ -325,6 +333,7 @@ export default class RedisCommandsQueue {
|
||||
}
|
||||
|
||||
this.#chainInExecution = lastCommandChainId;
|
||||
this.#waitingToBeSentCommandsLength -= size;
|
||||
}
|
||||
|
||||
parseResponse(data: Buffer): void {
|
||||
|
@@ -159,6 +159,7 @@ export default class RedisSocket extends EventEmitter {
|
||||
this.#createNetSocket();
|
||||
|
||||
socket
|
||||
.setNoDelay()
|
||||
.once('error', (err) => reject(err))
|
||||
.once(connectEvent, () => {
|
||||
socket
|
||||
|
Reference in New Issue
Block a user