RSS Git Download  Clone
Raw Blame History 2kB 55 lines
export default async (options) => {
    const { socket, payload } = options;

    try {
        if (!socket.p3xrs.ioredis) {
            socket.emit(options.responseEvent, { status: 'error', error: 'Not connected to Redis' })
            return
        }
        if (payload.enabled) {
            // Start MONITOR - need a dedicated connection since MONITOR blocks
            if (!socket.p3xrs.ioredisMonitor) {
                const redis = socket.p3xrs.ioredis

                // retry up to 3 times - redis.monitor() can fail with
                // "Command queue state error" if other commands are in flight
                let monitor
                for (let attempt = 0; attempt < 3; attempt++) {
                    try {
                        monitor = await redis.monitor()
                        break
                    } catch (e) {
                        if (attempt === 2) throw e
                        await new Promise(r => setTimeout(r, 200))
                    }
                }

                socket.p3xrs.ioredisMonitor = monitor

                socket.p3xrs.ioredisMonitor.on('monitor', (time, args, source, database) => {
                    socket.emit('monitor-data', {
                        time: time,
                        args: args,
                        source: source,
                        database: database,
                    })
                })

                console.info('MONITOR started for', socket.id)
            }
        } else {
            // Stop MONITOR
            if (socket.p3xrs.ioredisMonitor) {
                socket.p3xrs.ioredisMonitor.disconnect()
                socket.p3xrs.ioredisMonitor = undefined
                console.info('MONITOR stopped for', socket.id)
            }
        }

        socket.emit(options.responseEvent, { status: 'ok' })
    } catch (e) {
        console.error('Monitor error:', e)
        socket.emit(options.responseEvent, { status: 'error', error: e.message })
    }
}