feat: Sentinel mode support
- NewConnectionDialog: sentinel toggle + host/port/masterName/nodePassword form - connection.ts: use ioredis sentinels config when sentinelEnabled - Add sentinelEnabled/sentinelHost/sentinelPort/sentinelNodePassword to all types - i18n keys for all sentinel fields (zh-CN + en)
This commit is contained in:
@@ -17,6 +17,11 @@ export interface ConnectionOptions {
|
||||
tlsCertPath?: string
|
||||
tlsKeyPath?: string
|
||||
tlsRejectUnauthorized?: boolean
|
||||
sentinelEnabled?: boolean
|
||||
sentinelHost?: string
|
||||
sentinelPort?: number
|
||||
sentinelMasterName?: string
|
||||
sentinelNodePassword?: string
|
||||
sshEnabled?: boolean
|
||||
sshHost?: string
|
||||
sshPort?: number
|
||||
@@ -163,6 +168,48 @@ export async function connect(id: string, opts: ConnectionOptions): Promise<void
|
||||
let tunnelServer: ReturnType<typeof createServer> | undefined
|
||||
|
||||
try {
|
||||
if (opts.sentinelEnabled && opts.sentinelMasterName) {
|
||||
// Sentinel mode: connect via sentinel
|
||||
const sentinelOptions: RedisOptions = {
|
||||
sentinels: [{ host: opts.sentinelHost || opts.host, port: opts.sentinelPort || 26379 }],
|
||||
name: opts.sentinelMasterName,
|
||||
sentinelPassword: opts.sentinelNodePassword || undefined,
|
||||
username: opts.username || undefined,
|
||||
password: opts.password || undefined,
|
||||
stringNumbers: true,
|
||||
enableReadyCheck: true,
|
||||
connectTimeout: 10000,
|
||||
retryStrategy(times: number) {
|
||||
if (times > 3) return null
|
||||
return Math.min(times * 200, 1000)
|
||||
},
|
||||
maxRetriesPerRequest: 3,
|
||||
}
|
||||
if (opts.tls) {
|
||||
sentinelOptions.tls = {
|
||||
rejectUnauthorized: opts.tlsRejectUnauthorized || false,
|
||||
checkServerIdentity: () => undefined,
|
||||
}
|
||||
}
|
||||
const redis = new Redis(sentinelOptions)
|
||||
|
||||
redis.once('ready', () => {
|
||||
clients.set(id, { client: redis })
|
||||
resolve()
|
||||
})
|
||||
redis.once('error', (err: Error) => {
|
||||
redis.disconnect()
|
||||
reject(err)
|
||||
})
|
||||
setTimeout(() => {
|
||||
if (!clients.has(id)) {
|
||||
redis.disconnect()
|
||||
reject(new Error('连接超时,请检查主机和端口'))
|
||||
}
|
||||
}, 12000)
|
||||
return
|
||||
}
|
||||
|
||||
if (opts.sshEnabled) {
|
||||
const tunnel = await createSshTunnel(opts)
|
||||
sshClient = tunnel.sshClient
|
||||
|
||||
@@ -21,7 +21,11 @@ interface ConnectionConfig {
|
||||
sshPrivateKeyPath: string
|
||||
sshPassphrase: string
|
||||
cluster: boolean
|
||||
sentinelEnabled: boolean
|
||||
sentinelHost: string
|
||||
sentinelPort: number
|
||||
sentinelMasterName: string
|
||||
sentinelNodePassword: string
|
||||
separator: string
|
||||
order: number
|
||||
createdAt: number
|
||||
|
||||
Reference in New Issue
Block a user