<commit_before>const pkg = require('./package.json');

const redis = require('redis');
const path = require('path');
const fs = require('fs');
const once = require('once');

const NodeRateLimiter = require('node-rate-limiter');

const script = fs.readFileSync(path.join(__dirname, 'script.lua'), 'utf-8');

module.exports = RedisAdaptor;

RedisAdaptor.name = 'redis';
RedisAdaptor.ver = pkg.version;

function RedisAdaptor(opts) {
    opts = opts || {};
    opts.timeout = opts.timeout || NodeRateLimiter.defaultTimeout;
    opts.client = opts.client || redis.createClient();

    const adaptorOpts = opts;

    this.prepare = (callback) => prepare(adaptorOpts, callback); 
    this.reset = (id, callback) => reset(adaptorOpts, id, callback); 
    this.get = (id, opts, callback) => get(adaptorOpts, id, opts, callback);
}

function reset(adaptorOpts, id, callback) {
    const keyClient = 'ratelimiter.' + id;
    const keyClientTotal = keyClient + '.total';
    const keyClientLimit = keyClient + '.limit';

    const onDoneOnce = once(onDone);

    adaptorOpts.client
        .multi()
        .del(keyClientTotal)
        .del(keyClientLimit)
        .exec(onDoneOnce);

    let timerId = registerTimeout(`reset(${id})`, adaptorOpts.timeout, onDoneOnce);


    function onDone(err, res) {
        if (timerId) {
            clearTimeout(timerId);
            timerId = null;
        }

        callback(err, res);
    }
}

function get(adaptorOpts, id, opts, callback) {
    const limit = opts && opts.limit || NodeRateLimiter.defaultRateLimit;
    const expire = opts && opts.expire || NodeRateLimiter.defaultExpiration;
    
    const onEvalshaDoneOnce = once(onEvalshaDone);

    adaptorOpts.client.evalsha(adaptorOpts.scriptSha, 3, id, limit, expire, onEvalshaDoneOnce);
    let timerId = registerTimeout(`get(${id}, ${JSON.stringify(opts)})`, adaptorOpts.timeout, onEvalshaDoneOnce);


    function onEvalshaDone(err, res) {
        if (timerId) {
            clearTimeout(timerId);
            timerId = null;
        }

        if (err) {
            return callback(err);
        }

        const result = {
            limit: res[0], 
            remaining: res[0] - res[1] + 1, 
            reset: res[2]
        };
        callback(null, result);
    }
}

function prepare(adaptorOpts, callback) {
    if (adaptorOpts.scriptSha) {
        return callback(null);
    }

    adaptorOpts.client.script('load', script, onScriptLoaded);<commit_msg>refactoring<commit_after>const pkg = require('./package.json');

const redis = require('redis');
const path = require('path');
const fs = require('fs');
const once = require('once');

const NodeRateLimiter = require('node-rate-limiter');

const script = fs.readFileSync(path.join(__dirname, 'script.lua'), 'utf-8');

module.exports = RedisAdaptor;

RedisAdaptor.name = 'redis';
RedisAdaptor.ver = pkg.version;

function RedisAdaptor(opts) {
    opts = opts || {};
    opts.timeout = opts.timeout || NodeRateLimiter.defaultTimeout;
    opts.client = opts.client || redis.createClient();

    const adaptorOpts = opts;

    this.prepare = (callback) => prepare(adaptorOpts, callback); 
    this.reset = (id, callback) => reset(adaptorOpts, id, callback); 
    this.get = (id, opts, callback) => get(adaptorOpts, id, opts, callback);
}

function reset(adaptorOpts, id, callback) {
    const keyClient = 'ratelimiter.' + id;
    const keyClientTotal = keyClient + '.total';
    const keyClientLimit = keyClient + '.limit';

    const onDoneOnce = once(onDone);

    adaptorOpts.client
        .multi()
        .del(keyClientTotal)
        .del(keyClientLimit)
        .exec(onDoneOnce);

    let timerId = registerTimeout(`reset(${id})`, adaptorOpts.timeout, onDoneOnce);


    function onDone(err, res) {
        if (timerId) {
            timerId = clearTimeout(timerId);
        }

        callback(err, res);
    }
}

function get(adaptorOpts, id, opts, callback) {
    const limit = opts && opts.limit || NodeRateLimiter.defaultRateLimit;
    const expire = opts && opts.expire || NodeRateLimiter.defaultExpiration;
    
    const onEvalshaDoneOnce = once(onEvalshaDone);

    adaptorOpts.client.evalsha(adaptorOpts.scriptSha, 3, id, limit, expire, onEvalshaDoneOnce);
    let timerId = registerTimeout(`get(${id}, ${JSON.stringify(opts)})`, adaptorOpts.timeout, onEvalshaDoneOnce);


    function onEvalshaDone(err, res) {
        if (timerId) {
            timerId = clearTimeout(timerId);
        }

        if (err) {
            return callback(err);
        }

        const result = {
            limit: res[0], 
            remaining: res[0] - res[1] + 1, 
            reset: res[2]
        };
        callback(null, result);
    }
}

function prepare(adaptorOpts, callback) {
    if (adaptorOpts.scriptSha) {
        return callback(null);
    }

    adaptorOpts.client.script('load', script, onScriptLoaded);
{'fraction_non_alphanumeric': 0.13658736669401148, 'fraction_numerical': 0.002871205906480722, 'mean_word_length': 3.0139917695473253, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 9, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2662583', 'n_tokens_mistral': 1561, 'n_tokens_neox': 1538, 'n_words': 323}