/**
 * Copyright 2018 Twitter, Inc.
 * Licensed under the Apache License, Version 2.0
 * http://www.apache.org/licenses/LICENSE-2.0
 */ import { Context } from "sqrl" ; import { invariant } from "sqrl-common" ; import { MockRedisDatabase } from "./MockRedisDatabase" ; import { mockRateLimitFetch } from "../lua/rateLimitFetchLua" ; import { mockSessionize } from "../lua/sessionizeLua" ; import { RedisInterface , RateLimitOptions } from "../services/RedisInterface" ; export class MockRedisService implements RedisInterface , MockRedisDatabase { db = { } ; async rateLimitFetch ( ctx , key , opt ) { return mockRateLimitFetch ( this , key . toString ( "utf-8" ) , opt . maxAmount , opt . take , opt . at , opt . refillTimeMs , opt . refillAmount , opt . strict ) ; } async sessionize ( ctx , key , opt ) { return mockSessionize ( this , key . toString ( "utf-8" ) , opt . maxAmount , opt . take , opt . at , opt . refillTimeMs , opt . refillAmount ) ; } async increment ( ctx , bufferKey ) { const key = bufferKey . toString ( "hex" ) ; this . db [ key ] = this . db [ key ] || 0 ; this . db [ key ] ++ ; return this . db [ key ] ; } async get ( ctx , bufferKey ) { const key = bufferKey . toString ( "hex" ) ; if ( this . db . hasOwnProperty ( key ) ) { return this . db [ key ] ; } else { return null ; } } async del ( ctx , ... bufferKeys ) { let count = 0 ; for ( const bufferKey of bufferKeys ) { const key = bufferKey . toString ( "hex" ) ; if ( this . db . hasOwnProperty ( key ) ) { count += 1 ; delete this . db [ key ] ; } } return count ; } async set ( ctx , bufferKey , value , mode ) { const key = bufferKey . toString ( "hex" ) ; const exists = this . db . hasOwnProperty ( key ) ; if ( mode === "XX" && ! exists ) { return false ; } else if ( mode === "NX" && exists ) { return false ; } this . db [ key ] = value ; return true ; } async getList ( ctx , bufferKey ) { const key = bufferKey . toString ( "hex" ) ; if ( ! this . db . hasOwnProperty ( key ) ) { return [ ] ; } invariant ( Array . isArray ( this . db [ key ] ) , "Expected array in mock redis" ) ; return this . db [ key ] ; } async listPush ( ctx , bufferKey , ... values ) { const key = bufferKey . toString ( "hex" ) ; if ( ! this . db . hasOwnProperty ( key ) ) { this . db [ key ] = [ ] ; } invariant ( Array . isArray ( this . db [ key ] ) , "Expected array in mock redis" ) ; this . db [ key ] . push ( ... values . map ( ( value ) => { if ( typeof value === "number" ) { return "" + value ; } else if ( value instanceof Buffer ) { return value . toString ( "utf-8" ) ; } else { return value ; } } ) ) ; } async pfcount ( ctx , bufferKeys ) { const allKeys = bufferKeys . reduce ( ( accum , bufferKey ) => Object . assign ( { } , accum , this . db [ bufferKey . toString ( "hex" ) ] || { } ) , { } ) ; return Object . keys ( allKeys ) . length ; } async pfadd ( ctx , bufferKey , values ) { const key = bufferKey . toString ( "hex" ) ; this . db [ key ] = this . db [ key ] || { } ; for ( const value of values ) { this . db [ key ] [ value ] = 1 ; } } async expire ( ctx , bufferKey , seconds ) { } async mgetNumbers ( ctx , bufferKeys ) { return bufferKeys . map ( ( bufferKey ) => this . db [ bufferKey . toString ( "hex" ) ] || null ) ; } }