From 88cd7d64a0b61e39fa3b0f547b30abfa2e964332 Mon Sep 17 00:00:00 2001 From: Mykola Skrypets Date: Sun, 2 Aug 2026 23:07:34 +0300 Subject: [PATCH] fix: ensure enclosing ranges contain occurrences --- snapshots/output/enclosing-ranges-ts/index.ts | 2 +- snapshots/output/enclosing-ranges/range.js | 6 +++--- src/FileIndexer.ts | 9 +++++++-- src/main.test.ts | 16 ++++++++++++++++ 4 files changed, 27 insertions(+), 6 deletions(-) diff --git a/snapshots/output/enclosing-ranges-ts/index.ts b/snapshots/output/enclosing-ranges-ts/index.ts index 430c1451..6e8d6f73 100644 --- a/snapshots/output/enclosing-ranges-ts/index.ts +++ b/snapshots/output/enclosing-ranges-ts/index.ts @@ -1,9 +1,9 @@ // < definition enclosing-ranges-ts 1.0.0 `index.ts`/ +// < start enclosing_range enclosing-ranges-ts 1.0.0 `index.ts`/ // format-options: showRanges // < start enclosing_range enclosing-ranges-ts 1.0.0 `index.ts`/Foo# -// < start enclosing_range enclosing-ranges-ts 1.0.0 `index.ts`/ interface Foo { // ^^^ definition enclosing-ranges-ts 1.0.0 `index.ts`/Foo# bar: string diff --git a/snapshots/output/enclosing-ranges/range.js b/snapshots/output/enclosing-ranges/range.js index 4684c559..4455ece6 100644 --- a/snapshots/output/enclosing-ranges/range.js +++ b/snapshots/output/enclosing-ranges/range.js @@ -1,9 +1,9 @@ // < definition enclosing-ranges 0.0.1 `range.js`/ +// < start enclosing_range enclosing-ranges 0.0.1 `range.js`/ // format-options: showRanges -// < start enclosing_range enclosing-ranges 0.0.1 `range.js`/ -// ⌄ start enclosing_range enclosing-ranges 0.0.1 `range.js`/test. +// ⌄ start enclosing_range enclosing-ranges 0.0.1 `range.js`/test. const test = () => { // ^^^^ definition enclosing-ranges 0.0.1 `range.js`/test. const a = 'a' @@ -15,7 +15,7 @@ const test = () => { // ^ reference local 2 // ^ reference local 5 } -// ^ end enclosing_range enclosing-ranges 0.0.1 `range.js`/test. +// ^ end enclosing_range enclosing-ranges 0.0.1 `range.js`/test. // < start enclosing_range enclosing-ranges 0.0.1 `range.js`/test2(). function test2() { diff --git a/src/FileIndexer.ts b/src/FileIndexer.ts index 991ce9dc..18de358c 100644 --- a/src/FileIndexer.ts +++ b/src/FileIndexer.ts @@ -16,6 +16,7 @@ import { import { Input } from './Input' import { Packages } from './Packages' import { formatByteSizeAsHumanReadable } from './parseHumanByteSizeIntoNumber' +import { Position } from './Position' import { Range } from './Range' import * as scip from './scip' import { ScipSymbol } from './ScipSymbol' @@ -68,10 +69,14 @@ export class FileIndexer { if (symbol.isEmpty()) { return } + const sourceFileRange = Range.fromNode(this.sourceFile) this.pushOccurrence( new scip.scip.Occurrence({ range: [0, 0, 0], - enclosing_range: Range.fromNode(this.sourceFile).toLsif(), + enclosing_range: new Range( + new Position(0, 0), + sourceFileRange.end + ).toLsif(), symbol: symbol.value, symbol_roles: scip.scip.SymbolRole.Definition, }) @@ -206,7 +211,7 @@ export class FileIndexer { declaration.initializer && ts.isFunctionLike(declaration.initializer) ) { - enclosingRange = Range.fromNode(declaration.initializer).toLsif() + enclosingRange = Range.fromNode(declaration).toLsif() } else if ( ts.isFunctionDeclaration(declaration) || ts.isEnumDeclaration(declaration) || diff --git a/src/main.test.ts b/src/main.test.ts index 17b26125..cb121441 100644 --- a/src/main.test.ts +++ b/src/main.test.ts @@ -8,6 +8,7 @@ import { test } from 'uvu' import { Input } from './Input' import { indexCommand } from './main' +import { Range } from './Range' import * as scip from './scip' import { formatSnapshot } from './SnapshotTesting' @@ -74,6 +75,21 @@ for (const snapshotDirectory of snapshotDirectories) { throw new Error('empty LSIF index') } for (const document of index.documents) { + for (const occurrence of document.occurrences) { + if (occurrence.enclosing_range.length === 0) { + continue + } + const range = Range.fromLsif(occurrence.range) + const enclosingRange = Range.fromLsif(occurrence.enclosing_range) + if ( + enclosingRange.start.compare(range.start) > 0 || + enclosingRange.end.compare(range.end) < 0 + ) { + throw new Error( + `enclosing range does not contain occurrence for ${occurrence.symbol} in ${document.relative_path}` + ) + } + } const inputPath = path.join(inputRoot, document.relative_path) const relativeToInputDirectory = path.relative(inputDirectory, inputPath) const outputPath = path.resolve(outputDirectory, relativeToInputDirectory)