<commit_before>var Nohm = null;
exports.setNohm = function (originalNohm) {
  Nohm = originalNohm;
};

var async = require('async'),
    h = require(__dirname + '/helpers');

/**
 * Check if a given id exists in the DB.
 */
exports.exists = function (id, callback) {
  this.getClient().sismember(Nohm.prefix.idsets+this.modelName, id, function (err, found) {
    Nohm.logError(err);
    callback(!!found);
  });
};

var convertIdsToInt = function (ids, callback) {
  if (this.idGenerator === 'increment' && Array.isArray(ids)) {
    ids = ids.map(function (val) {
      return parseInt(val, 10);
    });
  }
  callback(ids);
}

/**
 * Retrieves the hash data by id and puts it into the properties.
 */
exports.load = function (id, callback) {
  var self = this;
  if (!id) {
    Nohm.logError('Trying to pass load() a wrong kind of id. Needs to be a number over 0. (still trying to load it though)');
  }
  this.getClient().hgetall(this.getHashKey(id), function (err, values) {
    var p, value,
        keys = values ? Object.keys(values) : [],
        return_props = {};
    if (err) {
      Nohm.logError('loading a hash produced an error: ' + err);
    }
    if (Array.isArray(keys) && keys.length > 0) {
      for (p in values) {
        var is_enumerable = values.hasOwnProperty(p);
        var is_meta = p === '__meta_version';
        var is_property = self.properties.hasOwnProperty(p);
        if (is_enumerable && is_property && ! is_meta) {
          value = values[p] !== null ? values[p].toString() : null;
          if (self.properties[p].load_pure) {
            self.properties[p].value = value;
          } else {
            self.p(p, value);
          }
          return_props[p] = self.p(p);
          self.__resetProp(p);
        } else if ( ! is_meta && ! self.properties.hasOwnProperty(p)) {
          Nohm.logError('WARNING: A hash in the DB contained a key ('+p+') that is not in the model definition. This might be because of model changes or database corruption/intrusion.')
        }
      }
      self.id = id;
      self.__inDB = true;
      self.__loaded = true;
    } else if (!err) {
      err = 'not found';
    }
    if (typeof(callback) === 'function') {
      callback.call(self, err, return_props);
    }
  });
};

/**
 * Finds ids of objects and loads them.
 */
exports.findAndLoad = function findAndLoad(searches, callback) {
  var self = this;
  this.find(searches, function (err, ids) {
    if (err) {
      callback(err, ids);
    } else if (ids.length === 0) {
      callback("not found", ids);
    } else {
      if (ids.length > 0) {
        async.map(ids, function (id, done) {
          var instance = Nohm.factory(self.modelName);
          instance.load(id, function (err) {
            done(err, instance);
          });
        }, callback);
      }
    }
  });
};

/**
 * Finds ids of objects by search arguments
 */
exports.find = function find(searches, callback) {
  var self = this, sets = [], zsetKeys = [], s, prop,
  returnFunction = function (err, values) {
    var found = [];
    Nohm.logError(err);
    if (Array.isArray(values) && values.length > 0) {
      values = values.forEach(function (val) {
        if (val) {
          found.push(val);
        }
      });
    } else if ( ! Array.isArray(values) && values !== null) {
      found = [values];
    } else if (values === null) {
      found = [];
    }
    convertIdsToInt(found, function (ids) {
      callback.call(self, err, ids);
    });
  },
  getSets = function (callback) {
    self.getClient().sinter(sets, callback);
  },
  getSingleZSet = function (zSet, callback) {
    var rangeCallback = function (err, values) {
      if (err) {
        callback(err);
      } else {
        callback(null, values);
      }
    };
    var options = zSet.options;
    if ( ! options.min && options.min !== 0)
      options.min = '-inf';
    if ( ! options.max && options.max !== 0)
      options.max = '+inf';
    if ( ! options.offset && options.offset !== 0)
      options.offset = '+inf';
    if (options.limit) {
      self.getClient().zrangebyscore(zSet.key, options.min, options.max,
                      'LIMIT', options.offset, options.limit,
                      rangeCallback);
    } else {
      self.getClient().zrangebyscore(zSet.key, options.min, options.max,
                      rangeCallback);
    }
  },
  getZSets = function (callback) {
    async.map(zsetKeys, getSingleZSet, function done (err, arr) {
      var ids = h.idIntersection.apply(null, arr);
      callback(err, ids);<commit_msg>Improved find() to find in descending order when min>max; Add endpoint options.<commit_after>var Nohm = null;
exports.setNohm = function (originalNohm) {
  Nohm = originalNohm;
};

var async = require('async'),
    h = require(__dirname + '/helpers');

/**
 * Check if a given id exists in the DB.
 */
exports.exists = function (id, callback) {
  this.getClient().sismember(Nohm.prefix.idsets+this.modelName, id, function (err, found) {
    Nohm.logError(err);
    callback(!!found);
  });
};

var convertIdsToInt = function (ids, callback) {
  if (this.idGenerator === 'increment' && Array.isArray(ids)) {
    ids = ids.map(function (val) {
      return parseInt(val, 10);
    });
  }
  callback(ids);
}

/**
 * Retrieves the hash data by id and puts it into the properties.
 */
exports.load = function (id, callback) {
  var self = this;
  if (!id) {
    Nohm.logError('Trying to pass load() a wrong kind of id. Needs to be a number over 0. (still trying to load it though)');
  }
  this.getClient().hgetall(this.getHashKey(id), function (err, values) {
    var p, value,
        keys = values ? Object.keys(values) : [],
        return_props = {};
    if (err) {
      Nohm.logError('loading a hash produced an error: ' + err);
    }
    if (Array.isArray(keys) && keys.length > 0) {
      for (p in values) {
        var is_enumerable = values.hasOwnProperty(p);
        var is_meta = p === '__meta_version';
        var is_property = self.properties.hasOwnProperty(p);
        if (is_enumerable && is_property && ! is_meta) {
          value = values[p] !== null ? values[p].toString() : null;
          if (self.properties[p].load_pure) {
            self.properties[p].value = value;
          } else {
            self.p(p, value);
          }
          return_props[p] = self.p(p);
          self.__resetProp(p);
        } else if ( ! is_meta && ! self.properties.hasOwnProperty(p)) {
          Nohm.logError('WARNING: A hash in the DB contained a key ('+p+') that is not in the model definition. This might be because of model changes or database corruption/intrusion.')
        }
      }
      self.id = id;
      self.__inDB = true;
      self.__loaded = true;
    } else if (!err) {
      err = 'not found';
    }
    if (typeof(callback) === 'function') {
      callback.call(self, err, return_props);
    }
  });
};

/**
 * Finds ids of objects and loads them.
 */
exports.findAndLoad = function findAndLoad(searches, callback) {
  var self = this;
  this.find(searches, function (err, ids) {
    if (err) {
      callback(err, ids);
    } else if (ids.length === 0) {
      callback("not found", ids);
    } else {
      if (ids.length > 0) {
        async.map(ids, function (id, done) {
          var instance = Nohm.factory(self.modelName);
          instance.load(id, function (err) {
            done(err, instance);
          });
        }, callback);
      }
    }
  });
};

/**
 * Finds ids of objects by search arguments
 */
exports.find = function find(searches, callback) {
  var self = this, sets = [], zsetKeys = [], s, prop,
  returnFunction = function (err, values) {
    var found = [];
    Nohm.logError(err);
    if (Array.isArray(values) && values.length > 0) {
      values = values.forEach(function (val) {
        if (val) {
          found.push(val);
        }
      });
    } else if ( ! Array.isArray(values) && values !== null) {
      found = [values];
    } else if (values === null) {
      found = [];
    }
    convertIdsToInt(found, function (ids) {
      callback.call(self, err, ids);
    });
  },
  getSets = function (callback) {
    self.getClient().sinter(sets, callback);
  },
  getSingleZSet = function (zSet, callback) {
    var rangeCallback = function (err, values) {
      if (err) {
        callback(err);
      } else {
        callback(null, values);
      }
    };
    var options = zSet.options;
    if ( ! options.min && options.min !== 0)
      options.min = '-inf';
    if ( ! options.max && options.max !== 0)
      options.max = '+inf';
    if ( ! options.offset && options.offset !== 0)
      options.offset = '+inf';

    var is_rev;
    if( (options.min == '+inf' && options.max != '+inf') || 
        (options.max == '-inf' && options.min != '-inf') || 
        (options.min > options.max) )
      is_rev = true;
    else
      is_rev = false;
    
    if ( ! options.endpoint ) {
      options.endpoint = '[]';
    } else {
      if ( options.endpoint.length == 1 ) {
        if ( options.endpoint[0] == ')' || options.endpoint[1] == ']' ) {
          options.endpoint = '[' + options.endpoint;
        } else if ( options.endpoint[0] == '(' || options.endpoint[1] == '[' ) {
          options.endpoint += ']';
        } else {
          return returnFunction('Invalid search parameters: endpoint expression is invalid.');
        }
      } else if ( options.endpoint.length != 2) {
        return returnFunction('Invalid search parameters: endpoint expression is invalid.');
      }
    }
    var endpoint_lt = options.endpoint[0] == '('; 
    var endpoint_gt = options.endpoint[1] == ')';

    if (options.limit) {
      if(is_rev)
        self.getClient().zrevrangebyscore(zSet.key, 
                      (endpoint_lt ? '(' : '') + options.min, 
                      (endpoint_gt ? '(': '') + options.max,
                      'LIMIT', options.offset, options.limit,
                      rangeCallback);
      else
        self.getClient().zrangebyscore(zSet.key, 
                      (endpoint_lt ? '(' : '') + options.min, 
                      (endpoint_gt ? '(': '') + options.max,
                      'LIMIT', options.offset, options.limit,
                      rangeCallback);
    } else {
      if(is_rev)
        self.getClient().zrevrangebyscore(zSet.key, 
                      (endpoint_lt ? '(' : '') + options.min, 
                      (endpoint_gt ? '(': '') + options.max,
                      rangeCallback);
      else
        self.getClient().zrangebyscore(zSet.key, 
                      (endpoint_lt ? '(' : '') + options.min, 
                      (endpoint_gt ? '(': '') + options.max,
                      rangeCallback);
    }
  },
  getZSets = function (callback) {
    async.map(zsetKeys, getSingleZSet, function done (err, arr) {
      var ids = h.idIntersection.apply(null, arr);
      callback(err, ids);
{'fraction_non_alphanumeric': 0.15343525511143857, 'fraction_numerical': 0.0025787437833855223, 'mean_word_length': 2.2013561320754715, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 11, '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': '2172825', 'n_tokens_mistral': 3448, 'n_tokens_neox': 3401, 'n_words': 831}