function narrowResultsIfPossible(context, entries) {
  const {
    indexMetadata,
    dbQueries,
    usedQueries
  } = context;
  const indexFields = new Map();
  indexMetadata.keyFields.forEach(([fieldName], positionInKey) => {
    // Every index key is [indexId, field1, field2, ...] and `indexMetadata.keyFields` contains [field1, field2, ...]
    // As `indexId` is in the first column the fields need to be offset by +1 for correct addressing
    indexFields.set(fieldName, positionInKey + 1);
  });
  const filtersToApply = [];

  for (const query of dbQueries) {
    const fieldName = (0, _query.dbQueryToDottedField)(query);
    const positionInKey = indexFields.get(fieldName);

    if (typeof positionInKey === `undefined`) {
      // No data for this field in index
      continue;
    }

    if (usedQueries.has(query)) {
      // Filter is already applied
      continue;
    }

    if (isMultiKeyIndex(context) && isNegatedQuery(query)) {
      // NE/NIN not supported with MultiKey indexes:
      //   MultiKey indexes include duplicates; negated queries will only filter some of those
      //   but may still incorrectly include others in final results
      continue;
    }

    const filter = (0, _query.getFilterStatement)(query);
    filtersToApply.push([filter, positionInKey]);
    usedQueries.add(query);
  }

  return filtersToApply.length === 0 ? entries : entries.filter(({
    key
  }) => {
    for (const [filter, fieldPositionInIndex] of filtersToApply) {
      const value = key[fieldPositionInIndex] === _createIndex.undefinedSymbol ? undefined : key[fieldPositionInIndex];

      if (!(0, _common.matchesFilter)(filter, value)) {
        // Mimic AND semantics
        return false;
      }
    }

    return true;
  });
}
/**
 * Takes results after the index scan and tries to filter them additionally with unused parts of the query.
 *
 * This is O(N) but the advantage is that it uses data available in the index.
 * So it effectively bypasses the `getNode()` call for such filters (with all associated deserialization complexity).
 *
 * Example:
 *   Imagine the index is: { foo: 1, bar: 1 }
 *
 * Now we run the query:
 *   sort: [`foo`]
 *   filter: { bar: { eq: `test` }}
 *
 * Initial filtering pass will have to perform a full index scan (because `bar` is the last field in the index).
 *
 * But we still have values of `bar` stored in the index itself,
 * so can filter by this value without loading the full node contents.
 */
Takes results after the index scan and tries to filter them additionally with unused parts of the query.
This is O(N) but the advantage is that it uses data available in the index.
So it effectively bypasses the `getNode()` call for such filters (with all associated deserialization complexity).

Imagine the index is: { foo: 1, bar: 1 }



Initial filtering pass will have to perform a full index scan (because `bar` is the last field in the index).

But we still have values of `bar` stored in the index itself,
so can filter by this value without loading the full node contents.
Takes results after the index scan and tries to filter them additionally with unused parts of the query . This is O ( N ) but the advantage is that it uses data available in the index . So it effectively bypasses the ` getNode () ` call for such filters ( with all associated deserialization complexity ) . Imagine the index is : { foo : 1 bar : 1 } Initial filtering pass will have to perform a full index scan ( because ` bar ` is the last field in the index ) . But we still have values of ` bar ` stored in the index itself so can filter by this value without loading the full node contents .
function narrowResultsIfPossible(context, entries) {
  const {
    indexMetadata,
    dbQueries,
    usedQueries
  } = context;
  const indexFields = new Map();
  indexMetadata.keyFields.forEach(([fieldName], positionInKey) => {
    indexFields.set(fieldName, positionInKey + 1);
  });
  const filtersToApply = [];
  for (const query of dbQueries) {
    const fieldName = (0, _query.dbQueryToDottedField)(query);
    const positionInKey = indexFields.get(fieldName);
    if (typeof positionInKey === `undefined`) {
      continue;
    }
    if (usedQueries.has(query)) {
      continue;
    }
    if (isMultiKeyIndex(context) && isNegatedQuery(query)) {
      continue;
    }
    const filter = (0, _query.getFilterStatement)(query);
    filtersToApply.push([filter, positionInKey]);
    usedQueries.add(query);
  }
  return filtersToApply.length === 0 ? entries : entries.filter(({
    key
  }) => {
    for (const [filter, fieldPositionInIndex] of filtersToApply) {
      const value = key[fieldPositionInIndex] === _createIndex.undefinedSymbol ? undefined : key[fieldPositionInIndex];
      if (!(0, _common.matchesFilter)(filter, value)) {
        return false;
      }
    }
    return true;
  });
}
function narrowResultsIfPossible ( context , entries ) { const { indexMetadata , dbQueries , usedQueries } = context ; const indexFields = new Map ( ) ; indexMetadata . keyFields . forEach ( ( [ fieldName ] , positionInKey ) => { indexFields . set ( fieldName , positionInKey + 1 ) ; } ) ; const filtersToApply = [ ] ; for ( const query of dbQueries ) { const fieldName = ( 0 , _query . dbQueryToDottedField ) ( query ) ; const positionInKey = indexFields . get ( fieldName ) ; if ( typeof positionInKey === ` ` ) { continue ; } if ( usedQueries . has ( query ) ) { continue ; } if ( isMultiKeyIndex ( context ) && isNegatedQuery ( query ) ) { continue ; } const filter = ( 0 , _query . getFilterStatement ) ( query ) ; filtersToApply . push ( [ filter , positionInKey ] ) ; usedQueries . add ( query ) ; } return filtersToApply . length === 0 ? entries : entries . filter ( ( { key } ) => { for ( const [ filter , fieldPositionInIndex ] of filtersToApply ) { const value = key [ fieldPositionInIndex ] === _createIndex . undefinedSymbol ? undefined : key [ fieldPositionInIndex ] ; if ( ! ( 0 , _common . matchesFilter ) ( filter , value ) ) { return false ; } } return true ; } ) ; }
Takes results after the index scan and tries to filter them additionally with unused parts of the query.
Takes results after the index scan and tries to filter them additionally with unused parts of the query .
// Every index key is [indexId, field1, field2, ...] and `indexMetadata.keyFields` contains [field1, field2, ...] // As `indexId` is in the first column the fields need to be offset by +1 for correct addressing // No data for this field in index // Filter is already applied // NE/NIN not supported with MultiKey indexes: //   MultiKey indexes include duplicates; negated queries will only filter some of those //   but may still incorrectly include others in final results // Mimic AND semantics