Press n or j to go to the next uncovered block, b, p or k for the previous block.
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 | 1x 1x 1x 76x 1x 76x | import COMMANDS from './commands/cluster'; import { RedisCommand, RedisModule, RedisModules } from './commands'; import { RedisCommandSignature } from './client'; import { RedisSocketOptions } from './socket'; import RedisClusterSlots from './cluster-slots'; export interface RedisClusterOptions<M = RedisModules> { rootNodes: Array<RedisSocketOptions>; modules?: M; useReplicas?: boolean; maxCommandRedirections?: number; } type WithCommands = { [P in keyof typeof COMMANDS]: RedisCommandSignature<(typeof COMMANDS)[P]> }; type WithModules<M extends Array<RedisModule>> = { [P in keyof M[number]]: RedisCommandSignature<M[number][P]> }; export type RedisClusterType<M extends RedisModules> = WithCommands & WithModules<M> & RedisCluster; export default class RedisCluster { static defineCommand(on: any, name: string, command: RedisCommand): void { on[name] = async function (...args: Array<unknown>): Promise<unknown> { const transformedArguments = command.transformArguments(...args); return command.transformReply( await this.sendCommand( transformedArguments, command.FIRST_KEY_INDEX, command.IS_READ_ONLY ) ); }; } static create<M extends RedisModules>(options: RedisClusterOptions): RedisClusterType<M> { return <any>new RedisCluster(options); } readonly #options: RedisClusterOptions; readonly #slots: RedisClusterSlots; constructor(options: RedisClusterOptions) { this.#options = options; this.#slots = new RedisClusterSlots(options); } async connect(): Promise<void> { return this.#slots.connect(); } async sendCommand<T = unknown>(args: Array<string>, firstKeyIndex?: number, isReadOnly?: boolean, redirections: number = 0): Promise<T> { const firstKey = firstKeyIndex ? args[firstKeyIndex] : undefined, client = this.#slots.getClient(firstKey, isReadOnly); try { return await client.sendCommand(args); } catch (err) { if (err.message.startsWith('ASK')) { // TODO } else if (err.message.startsWith('MOVED')) { await this.#slots.discover(); if (redirections < (this.#options.maxCommandRedirections ?? 16)) { return this.sendCommand(args, firstKeyIndex, isReadOnly, redirections + 1); } } throw err; } } disconnect(): Promise<void> { return this.#slots.disconnect(); } } for (const [name, command] of Object.entries(COMMANDS)) { RedisCluster.defineCommand(RedisCluster.prototype, name, command); } |