{"record":{"id":"f28c4934f3397ffa","repo":"krisk/Fuse","slug":"invalid-doc-index-must-be-a-non-negative-integer-f28c49","errorCode":null,"errorMessage":"Invalid doc index: must be a non-negative integer within the bounds of the docs array","messagePattern":"Invalid doc index: must be a non-negative integer within the bounds of the docs array","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"src/tools/FuseIndex.ts","lineNumber":93,"sourceCode":"      }\n    } else {\n      // List is Array<Object>\n      for (let i = 0; i < len; i++) {\n        this.records[recordCount++] = this._createObjectRecord(this.docs[i], i)\n      }\n    }\n\n    this.records.length = recordCount\n    this.norm.clear()\n  }\n  // Appends a record for `doc` at `docIndex` (the doc's position in the source\n  // array). Returns the appended record, or null when `doc` is a blank string\n  // (those are skipped at record creation; see `_createStringRecord`). Callers\n  // use the return value to gate downstream bookkeeping like the inverted\n  // index, which must not be touched when no record was produced.\n  add(doc: T, docIndex: number): IndexRecord | null {\n    if (!Number.isInteger(docIndex) || docIndex < 0) {\n      throw new Error(ErrorMsg.INVALID_DOC_INDEX)\n    }\n\n    if (isString(doc)) {\n      const record = this._createStringRecord(\n        doc as unknown as string,\n        docIndex\n      )\n      if (record) {\n        this.records.push(record)\n      }\n      return record\n    }\n\n    const record = this._createObjectRecord(doc, docIndex)\n    this.records.push(record)\n    return record\n  }\n  // Removes the record for the doc at the specified source-array (docs) index.","sourceCodeStart":75,"sourceCodeEnd":111,"githubUrl":"https://github.com/krisk/Fuse/blob/edf2fb608eca0461508d1d71317e6e58309ffada/src/tools/FuseIndex.ts#L75-L111","documentation":"Thrown by FuseIndex.add when docIndex is not an integer or is negative, violating the contract that each doc is added at a valid non-negative integer position within the docs array. The index stores records keyed by this position, so an invalid value would corrupt bookkeeping (e.g. the inverted index).","triggerScenarios":"Calling index.add(doc, docIndex) with a negative number, a float (e.g. 1.5), NaN, or a non-number coerced through arithmetic — Number.isInteger check fails. (Note: passing an index >= docs.length does not throw here; the bounds clause applies to the documented contract/other paths.)","commonSituations":"Manually maintaining a docs array while removing items and computing the next index with a stale length; off-by-one after splicing (length-2 used as next index becomes -1 on empty array); parsing doc indices from strings with parseFloat instead of parseInt.","solutions":["Pass the correct array position: docs.length - 1 for the last appended item, or track the index explicitly when splicing.","Guard before calling: if (!Number.isInteger(i) || i < 0) skip or fix the index.","Use docs.push(doc) and add(doc, docs.length - 1) together so the indices stay in sync.","Compute indices with Math.floor/parseInt from strings, never parseFloat or raw string arithmetic."],"exampleFix":"// before\nconst idx = docs.indexOf(doc); index.add(doc, idx) // -1 when absent\n// after\nconst idx = docs.indexOf(doc)\nif (idx === -1) { docs.push(doc); index.add(doc, docs.length - 1) } else { index.add(doc, idx) }","handlingStrategy":"validation","validationCode":"function canAdd(docs, doc, i) { return Number.isInteger(i) && i >= 0 && i < docs.length; }\nif (!canAdd(docs, doc, i)) throw new Error('bad docIndex: ' + i);","typeGuard":"function isValidDocIndex(i: unknown): i is number {\n  return typeof i === 'number' && Number.isInteger(i) && i >= 0;\n}","tryCatchPattern":"try {\n  const rec = index.add(doc, i);\n} catch (e) {\n  if (String(e.message).includes('Invalid doc index')) {\n    // recompute the index from the docs array and retry once\n  } else throw e;\n}","preventionTips":["Always pair docs.push(doc) with index.add(doc, docs.length - 1)","Never derive indices from indexOf without handling -1","Use integer arithmetic (parseInt/Math.floor), never parseFloat on doc positions","Keep the docs array and index mutations in one helper so they can't desync"],"tags":["indexing","validation","arguments"],"backgroundTag":"invalid-doc-index","analyzedSha":"edf2fb608eca0461508d1d71317e6e58309ffada","analyzedAt":"2026-09-02T02:46:54.623Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-09T06:17:21.866Z"}